feat: 🎸 Add serializer and adapter for storage bucket (#117)

* feat: 🎸 Add serializer and adapter for storage bucket

✅ Closes: ICU-8358
This commit is contained in:
Zhihe Li authored and GitHub committed 2023-03-15 15:18:02 -04:00
1 parent a28e7810e7
commit 5992829fa2
8 files changed
+175 -2

No files matched your search

@@ -0,0 +1,23 @@
import ApplicationAdapter from './application';
export default class StorageBucketAdapter extends ApplicationAdapter {
/**
* Overrides the default `buildURL` such that on _create_, URLs for records of
* type `plugin` get an extra query parameter `?plugin_name`. All other
* request types behave as normal.
*
* @override
* @param {string} modelName
* @param {string} id
* @return {string} url
* @return {string} requestType
*/
buildURL(modelName, id, snapshot, requestType) {
let url = super.buildURL(...arguments);
const pluginName = snapshot?.attr('plugin')?.name;
if (requestType === 'createRecord' && pluginName) {
url = `${url}?plugin_name=${pluginName}`;
}
return url;
}
}
@@ -72,7 +72,7 @@ export default class GeneratedStorageBucketModel extends BaseModel {
readOnly: true,
isNestedAttribute: true,
})
client_secret_hmac;
secrets_hmac;
@attr('string', {
isNestedSecret: true,
@@ -0,0 +1,13 @@
import ApplicationSerializer from './application';
export default class StorageBucketSerializer extends ApplicationSerializer {
normalize(typeClass, hash, ...rest) {
const normalizedHash = structuredClone(hash);
const normalized = super.normalize(typeClass, normalizedHash, ...rest);
// Remove secret fields
delete normalized.data.attributes.access_key_id;
delete normalized.data.attributes.secret_access_key;
return normalized;
}
}
@@ -0,0 +1 @@
export { default } from 'api/adapters/storage-bucket';
@@ -0,0 +1 @@
export { default } from 'api/serializers/storage-bucket';
+7 -1
View File
@@ -14,6 +14,7 @@ import { targetHandler } from './route-handlers/target';
import { pickRandomStatusString } from './factories/session';
import initializeMockIPC from './scenarios/ipc';
import makeBooleanFilter from './helpers/bexpr-filter';
import { faker } from '@faker-js/faker';
const isTesting = environmentConfig.environment === 'test';
@@ -668,7 +669,7 @@ function routes() {
this.patch('/storage-buckets/:id');
this.post(
'/storage-buckets',
({ storageBuckets }, { queryParams: { plugin_name } }) => {
function ({ storageBuckets }, { queryParams: { plugin_name } }) {
const attrs = this.normalizedRequestAttrs();
if (plugin_name) {
attrs.type = 'plugin';
@@ -676,6 +677,11 @@ function routes() {
name: plugin_name,
};
}
// Remove the secrets and add the hmac in the response
delete attrs.secrets;
attrs.secrets_hmac = faker.git.commitSha();
return storageBuckets.create(attrs);
}
);
@@ -0,0 +1,30 @@
import { module, test } from 'qunit';
import { setupTest } from 'ember-qunit';
module('Unit | Adapter | storage bucket', function (hooks) {
setupTest(hooks);
test('it generates correct createRecord URLs for storage buckets with extra query parameter ?plugin_name', function (assert) {
assert.expect(1);
const scopeID = 'o_1';
const mockSnapshot = {
adapterOptions: {
scopeID,
},
attr() {
return { name: 'aws_s3' };
},
};
const adapter = this.owner.lookup('adapter:storage-bucket');
const createRecordURL = adapter.buildURL(
'storage-bucket',
null,
mockSnapshot,
'createRecord'
);
assert.strictEqual(
createRecordURL,
'/v1/storage-buckets?plugin_name=aws_s3'
);
});
});
@@ -0,0 +1,99 @@
import { module, test } from 'qunit';
import { setupTest } from 'ember-qunit';
import {
TYPE_STORAGE_BUCKET_PLUGIN_AWS_S3,
TYPE_STORAGE_BUCKET_PLUGIN,
} from 'api/models/storage-bucket';
module('Unit | Serializer | storage bucket', function (hooks) {
setupTest(hooks);
test('it serializes records', function (assert) {
let store = this.owner.lookup('service:store');
let record = store.createRecord('storage-bucket', {});
let serializedRecord = record.serialize();
assert.ok(serializedRecord);
});
test('it serializes a new aws plugin as expected', async function (assert) {
assert.expect(1);
const store = this.owner.lookup('service:store');
const record = store.createRecord('storage-bucket', {
compositeType: TYPE_STORAGE_BUCKET_PLUGIN_AWS_S3,
name: 'AWS',
description: 'this has an aws plugin',
bucket_name: 'bucketname',
bucket_prefix: 'bucketprefix',
worker_filter: 'workerfilter',
region: 'eu-west-1',
access_key_id: 'foobars',
secret_access_key: 'testing',
secrets_hmac: 'hmac',
});
const expectedResult = {
name: 'AWS',
description: 'this has an aws plugin',
type: TYPE_STORAGE_BUCKET_PLUGIN,
bucket_name: 'bucketname',
bucket_prefix: 'bucketprefix',
worker_filter: 'workerfilter',
attributes: {
region: 'eu-west-1',
},
secrets: {
access_key_id: 'foobars',
secret_access_key: 'testing',
},
};
assert.deepEqual(record.serialize(), expectedResult);
});
test('it normalizes correctly', function (assert) {
assert.expect(1);
const store = this.owner.lookup('service:store');
const serializer = store.serializerFor('storage-bucket');
const hostSetModelClass = store.createRecord('storage-bucket').constructor;
const payload = {
id: '1',
version: 1,
name: 'AWS',
description: 'this has an aws plugin',
type: TYPE_STORAGE_BUCKET_PLUGIN,
bucket_name: 'bucketname',
bucket_prefix: 'bucketprefix',
worker_filter: 'workerfilter',
attributes: {
region: 'eu-west-1',
},
secrets_hmac: 'this is secret',
};
const normalized = serializer.normalizeSingleResponse(
store,
hostSetModelClass,
payload
);
assert.deepEqual(normalized, {
included: [],
data: {
id: '1',
attributes: {
type: TYPE_STORAGE_BUCKET_PLUGIN,
version: 1,
authorized_actions: [],
name: 'AWS',
description: 'this has an aws plugin',
bucket_name: 'bucketname',
bucket_prefix: 'bucketprefix',
worker_filter: 'workerfilter',
secrets_hmac: 'this is secret',
region: 'eu-west-1',
},
type: 'storage-bucket',
relationships: {},
},
});
});
});