web/satellite: generate gateway credentials for objects page

WHAT:
generate gateway credentials that will be used to instantiate s3 client

WHY:
for s3 client that will be used to manage buckets

Change-Id: I6d654e48c41925b72e11ec3edde3dc54f5290d42
This commit is contained in:
Vitalii Shpital 2021-03-18 21:22:46 +02:00
parent 1c696168c5
commit 346b85b66d
7 changed files with 73 additions and 12 deletions

View File

@ -156,10 +156,11 @@ export class AccessGrantsApiGql extends BaseGql implements AccessGrantsApi {
* Used to get gateway credentials using access grant.
*
* @param accessGrant - generated access grant
* @param optionalURL - optional requestURL
* @throws Error
*/
public async getGatewayCredentials(accessGrant: string): Promise<GatewayCredentials> {
const requestURL: string = MetaUtils.getMetaContent('gateway-credentials-request-url');
public async getGatewayCredentials(accessGrant: string, optionalURL?: string): Promise<GatewayCredentials> {
const requestURL: string = optionalURL || MetaUtils.getMetaContent('gateway-credentials-request-url');
if (!requestURL) throw new Error('Cannot get gateway credentials: request URL is not provided');
const path = `${requestURL}/v1/access`;

View File

@ -261,7 +261,7 @@ export default class ResultStep extends Vue {
this.isLoading = true;
try {
await this.$store.dispatch(ACCESS_GRANTS_ACTIONS.GET_GATEWAY_CREDENTIALS, this.access);
await this.$store.dispatch(ACCESS_GRANTS_ACTIONS.GET_GATEWAY_CREDENTIALS, {accessGrant: this.access});
await this.$notify.success('Gateway credentials were generated successfully');
this.areKeysVisible = true;

View File

@ -6,7 +6,7 @@
<div class="buckets-view__title-area">
<h1 class="buckets-view__title-area__title">Buckets</h1>
</div>
<div class="buckets-view__loader" v-if="isLoading"></div>
<div class="buckets-view__loader" v-if="isLoading"/>
</div>
</template>
@ -16,10 +16,15 @@ import { Component, Vue } from 'vue-property-decorator';
import { RouteConfig } from '@/router';
import { ACCESS_GRANTS_ACTIONS } from '@/store/modules/accessGrants';
import { OBJECTS_ACTIONS } from '@/store/modules/objects';
import { AccessGrant, GatewayCredentials } from '@/types/accessGrants';
import { MetaUtils } from '@/utils/meta';
@Component
export default class BucketsView extends Vue {
private readonly FILE_BROWSER_AG_NAME: string = 'Web file browser API key';
private worker: Worker;
private grantWithPermissions: string = '';
private accessGrant: string = '';
public isLoading: boolean = true;
@ -35,10 +40,65 @@ export default class BucketsView extends Vue {
}
try {
const accessGrant = await this.$store.dispatch(ACCESS_GRANTS_ACTIONS.CREATE, this.FILE_BROWSER_AG_NAME);
await this.$store.dispatch(OBJECTS_ACTIONS.SET_ACCESS_GRANT, accessGrant);
const cleanAPIKey: AccessGrant = await this.$store.dispatch(ACCESS_GRANTS_ACTIONS.CREATE, this.FILE_BROWSER_AG_NAME);
this.worker = this.$store.state.accessGrantsModule.accessGrantsWebWorker;
this.worker.onmessage = (event: MessageEvent) => {
const data = event.data;
if (data.error) {
throw new Error(data.error);
}
this.grantWithPermissions = data.value;
};
const now = new Date();
const inADay = new Date(now.setDate(now.getDate() + 1));
await this.worker.postMessage({
'type': 'SetPermission',
'isDownload': true,
'isUpload': true,
'isList': true,
'isDelete': true,
'buckets': [],
'apiKey': cleanAPIKey.secret,
'notBefore': now.toISOString(),
'notAfter': inADay.toISOString(),
});
// Timeout is used to give some time for web worker to return value.
setTimeout(() => {
this.worker.onmessage = (event: MessageEvent) => {
const data = event.data;
if (data.error) {
throw new Error(data.error);
}
this.accessGrant = data.value;
};
const satelliteNodeURL: string = MetaUtils.getMetaContent('satellite-nodeurl');
this.worker.postMessage({
'type': 'GenerateAccess',
'apiKey': this.grantWithPermissions,
'passphrase': this.$route.params.passphrase,
'projectID': this.$store.getters.selectedProject.id,
'satelliteNodeURL': satelliteNodeURL,
});
// Timeout is used to give some time for web worker to return value.
setTimeout(async () => {
await this.$store.dispatch(OBJECTS_ACTIONS.SET_ACCESS_GRANT, this.accessGrant);
// TODO: use this value until all the satellites will have this URL set.
const gatewayURL = 'https://auth.tardigradeshare.io';
const gatewayCredentials: GatewayCredentials = await this.$store.dispatch(ACCESS_GRANTS_ACTIONS.GET_GATEWAY_CREDENTIALS, {accessGrant: this.accessGrant, optionalURL: gatewayURL});
await this.$store.dispatch(OBJECTS_ACTIONS.SET_GATEWAY_CREDENTIALS, gatewayCredentials);
}, 1000);
}, 1000);
} catch (error) {
await this.$notify.error(error.message);
await this.$notify.error(`Failed to setup Objects view. ${error.message}`);
return;
}

View File

@ -214,8 +214,8 @@ export function makeAccessGrantsModule(api: AccessGrantsApi): StoreModule<Access
deleteAccessGrantsByNameAndProjectID: async function({state, rootGetters}: any, name: string): Promise<void> {
await api.deleteByNameAndProjectID(name, rootGetters.selectedProject.id);
},
getGatewayCredentials: async function({state, commit}: any, accessGrant: string): Promise<GatewayCredentials> {
const credentials: GatewayCredentials = await api.getGatewayCredentials(accessGrant);
getGatewayCredentials: async function({commit}: any, payload): Promise<GatewayCredentials> {
const credentials: GatewayCredentials = await api.getGatewayCredentials(payload.accessGrant, payload.optionalURL);
commit(SET_GATEWAY_CREDENTIALS, credentials);

View File

@ -6,7 +6,7 @@ import { GatewayCredentials } from '@/types/accessGrants';
export const OBJECTS_ACTIONS = {
CLEAR: 'clearObjects',
GET_GATEWAY_CREDENTIALS: 'getGatewayCredentials',
SET_GATEWAY_CREDENTIALS: 'setGatewayCredentials',
SET_ACCESS_GRANT: 'setAccessGrant',
};

View File

@ -47,7 +47,7 @@ export interface AccessGrantsApi {
* @returns GatewayCredentials
* @throws Error
*/
getGatewayCredentials(accessGrant: string): Promise<GatewayCredentials>;
getGatewayCredentials(accessGrant: string, optionalURL?: string): Promise<GatewayCredentials>;
}
/**

View File

@ -36,7 +36,7 @@ export class AccessGrantsMock implements AccessGrantsApi {
return Promise.resolve();
}
getGatewayCredentials(accessGrant: string): Promise<GatewayCredentials> {
getGatewayCredentials(accessGrant: string, optionalURL?: string): Promise<GatewayCredentials> {
return Promise.resolve(new GatewayCredentials('testCredId', new Date(), 'testAccessKeyId', 'testSecret', 'testEndpoint'));
}
}