From b33a4d0b1d4c295b08b84c968ada6c4a52e57856 Mon Sep 17 00:00:00 2001 From: Carlos Alcaide Corvo Date: Thu, 10 Feb 2022 11:43:30 -0800 Subject: [PATCH 1/6] =?UTF-8?q?refactor:=20=F0=9F=92=A1=20Refactor=20app?= =?UTF-8?q?=20normalize=20and=20host=20catalog=20normalize?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Refactor app normalize to deal with nestedAttributes and nestedSecrets as expected, before it was not working as expected. Refactor the host catalog normalize method. Add normalize test on host catalog to validate changes on normalize methods. --- addons/api/addon/serializers/application.js | 12 +- addons/api/addon/serializers/host-catalog.js | 8 + .../unit/serializers/host-catalog-test.js | 163 +++++++++++++++++- 3 files changed, 173 insertions(+), 10 deletions(-) diff --git a/addons/api/addon/serializers/application.js b/addons/api/addon/serializers/application.js index 29f3fa1b4..6882bd190 100644 --- a/addons/api/addon/serializers/application.js +++ b/addons/api/addon/serializers/application.js @@ -236,7 +236,7 @@ export default class ApplicationSerializer extends RESTSerializer { typeClass.attributes.forEach((attribute) => { const { isNestedAttribute } = attribute.options; const attributeValue = hash.attributes?.[attribute.name]; - if (isNestedAttribute && attributeValue) { + if (isNestedAttribute && typeof attributeValue != 'undefined') { hash[attribute.name] = attributeValue; } }); @@ -261,7 +261,15 @@ export default class ApplicationSerializer extends RESTSerializer { name, options: { isNestedSecret }, } = attribute; - if (isNestedSecret) hash[name] = null; + const attributeValue = hash.secrets?.[name]; + + // FIXME: This could be improved + if (isNestedSecret) { + hash[name] = null; + if (attributeValue) { + hash[name] = attributeValue; + } + } }); return hash; } diff --git a/addons/api/addon/serializers/host-catalog.js b/addons/api/addon/serializers/host-catalog.js index 77c78c680..f5d1cd983 100644 --- a/addons/api/addon/serializers/host-catalog.js +++ b/addons/api/addon/serializers/host-catalog.js @@ -1,4 +1,5 @@ import ApplicationSerializer from './application'; +import { copy } from 'ember-copy'; const fieldsByType = { aws: [ @@ -56,4 +57,11 @@ export default class HostCatalogSerializer extends ApplicationSerializer { delete serialized.secrets; return serialized; } + + normalize(typeClass, hash, ...rest) { + let normalizedHash = copy(hash, true); + const normalized = super.normalize(typeClass, normalizedHash, ...rest); + delete normalized.data.attributes.attributes; + return normalized; + } } diff --git a/addons/api/tests/unit/serializers/host-catalog-test.js b/addons/api/tests/unit/serializers/host-catalog-test.js index d82869348..2811dea39 100644 --- a/addons/api/tests/unit/serializers/host-catalog-test.js +++ b/addons/api/tests/unit/serializers/host-catalog-test.js @@ -4,14 +4,6 @@ import { setupTest } from 'ember-qunit'; module('Unit | Serializer | host catalog', function (hooks) { setupTest(hooks); - // Replace this with your real tests. - test('it exists', function (assert) { - const store = this.owner.lookup('service:store'); - const serializer = store.serializerFor('host-catalog'); - - assert.ok(serializer); - }); - test('it serializes records', function (assert) { const store = this.owner.lookup('service:store'); const record = store.createRecord('host-catalog', {}); @@ -171,4 +163,159 @@ module('Unit | Serializer | host catalog', function (hooks) { }; assert.deepEqual(record.serialize(), expectedResult); }); + + test('it normalizes an static host catalog as expected', function (assert) { + assert.expect(1); + const store = this.owner.lookup('service:store'); + const serializer = store.serializerFor('host-catalog'); + const hostCatalog = store.createRecord('host-catalog').constructor; + const payload = { + id: '1', + name: 'Host catalog test', + description: 'Test description', + authorized_actions: ['no-op'], + type: 'static', + }; + const normalized = serializer.normalizeSingleResponse( + store, + hostCatalog, + payload + ); + assert.deepEqual(normalized, { + data: { + id: '1', + type: 'host-catalog', + attributes: { + name: 'Host catalog test', + description: 'Test description', + authorized_actions: ['no-op'], + type: 'static', + access_key_id: null, + secret_access_key: null, + secret_id: null, + secret_value: null, + }, + relationships: {}, + }, + included: [], + }); + }); + + test('it normalizes an aws plugin type host catalog as expected', function (assert) { + assert.expect(1); + const store = this.owner.lookup('service:store'); + const serializer = store.serializerFor('host-catalog'); + const hostCatalog = store.createRecord('host-catalog').constructor; + const payload = { + id: '1', + name: 'Host catalog test', + description: 'Test description', + authorized_actions: ['no-op'], + type: 'plugin', + plugin: { + id: 'plugin-id-5', + name: 'aws', + description: 'aws host catalog', + }, + attributes: { + disable_credential_rotation: false, + region: 'Illinois', + }, + secrets: { + access_key_id: '0xF3B0a6f8', + secret_access_key: 'zq{2:IVc8@W^', + }, + }; + const normalized = serializer.normalizeSingleResponse( + store, + hostCatalog, + payload + ); + assert.deepEqual(normalized, { + data: { + id: '1', + type: 'host-catalog', + attributes: { + name: 'Host catalog test', + type: 'plugin', + description: 'Test description', + authorized_actions: ['no-op'], + plugin: { + id: 'plugin-id-5', + name: 'aws', + description: 'aws host catalog', + }, + disable_credential_rotation: false, + region: 'Illinois', + access_key_id: '0xF3B0a6f8', + secret_access_key: 'zq{2:IVc8@W^', + secret_id: null, + secret_value: null, + }, + relationships: {}, + }, + included: [], + }); + }); + + test('it normalizes an azure plugin type host catalog as expected', function (assert) { + assert.expect(1); + const store = this.owner.lookup('service:store'); + const serializer = store.serializerFor('host-catalog'); + const hostCatalog = store.createRecord('host-catalog').constructor; + const payload = { + id: '1', + name: 'Host catalog test', + description: 'Test description', + authorized_actions: ['no-op', 'read', 'update', 'delete'], + type: 'plugin', + plugin: { + id: 'plugin-id-6', + name: 'azure', + description: 'azure host catalog', + }, + attributes: { + disable_credential_rotation: true, + tenant_id: 'tenant', + client_id: 'client', + subscription_id: 'subscription', + }, + secrets: { + secret_id: '0xF3B0a6f8', + secret_value: 'zq{2:IVc8@W^', + }, + }; + const normalized = serializer.normalizeSingleResponse( + store, + hostCatalog, + payload + ); + assert.deepEqual(normalized, { + data: { + id: '1', + type: 'host-catalog', + attributes: { + name: 'Host catalog test', + type: 'plugin', + description: 'Test description', + authorized_actions: ['no-op', 'read', 'update', 'delete'], + plugin: { + id: 'plugin-id-6', + name: 'azure', + description: 'azure host catalog', + }, + disable_credential_rotation: true, + secret_id: '0xF3B0a6f8', + secret_value: 'zq{2:IVc8@W^', + client_id: 'client', + tenant_id: 'tenant', + subscription_id: 'subscription', + access_key_id: null, + secret_access_key: null, + }, + relationships: {}, + }, + included: [], + }); + }); }); From e1282bb870d4ad49352a1da9b33ea993e005309b Mon Sep 17 00:00:00 2001 From: Carlos Alcaide Corvo Date: Thu, 10 Feb 2022 11:47:30 -0800 Subject: [PATCH 2/6] Fix conditional to check for undefined --- addons/api/addon/serializers/application.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/addons/api/addon/serializers/application.js b/addons/api/addon/serializers/application.js index 6882bd190..dcc33eff6 100644 --- a/addons/api/addon/serializers/application.js +++ b/addons/api/addon/serializers/application.js @@ -266,7 +266,7 @@ export default class ApplicationSerializer extends RESTSerializer { // FIXME: This could be improved if (isNestedSecret) { hash[name] = null; - if (attributeValue) { + if (typeof attributeValue != 'undefined') { hash[name] = attributeValue; } } From b6f8e001f07e709f340a6caa3e5fb7d65cb9e267 Mon Sep 17 00:00:00 2001 From: dharini Date: Thu, 10 Feb 2022 18:22:14 -0800 Subject: [PATCH 3/6] =?UTF-8?q?chore:=20=F0=9F=A4=96=20hide=20actions=20fo?= =?UTF-8?q?r=20plugin=20host?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../host-catalogs/host-catalog/host-sets/host-set/hosts.hbs | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/ui/admin/app/templates/scopes/scope/host-catalogs/host-catalog/host-sets/host-set/hosts.hbs b/ui/admin/app/templates/scopes/scope/host-catalogs/host-catalog/host-sets/host-set/hosts.hbs index 80ba8a4f8..ae8b4183d 100644 --- a/ui/admin/app/templates/scopes/scope/host-catalogs/host-catalog/host-sets/host-set/hosts.hbs +++ b/ui/admin/app/templates/scopes/scope/host-catalogs/host-catalog/host-sets/host-set/hosts.hbs @@ -1,14 +1,15 @@ {{page-title (t 'resources.host.title_plural')}} {{#if @model.hosts}} - {{t 'form.name.label'}} {{t 'form.type.label'}} {{t 'form.id.label'}} - {{t 'titles.actions'}} + {{#if @model.isStatic}} + {{t 'titles.actions'}} + {{/if}} From 0776ec1af9f8a71d26c8e62be40a208ac1a0033f Mon Sep 17 00:00:00 2001 From: Dharini Jeeva Date: Thu, 10 Feb 2022 18:24:30 -0800 Subject: [PATCH 4/6] Update hosts.hbs --- .../host-catalogs/host-catalog/host-sets/host-set/hosts.hbs | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/ui/admin/app/templates/scopes/scope/host-catalogs/host-catalog/host-sets/host-set/hosts.hbs b/ui/admin/app/templates/scopes/scope/host-catalogs/host-catalog/host-sets/host-set/hosts.hbs index ae8b4183d..d78229fe4 100644 --- a/ui/admin/app/templates/scopes/scope/host-catalogs/host-catalog/host-sets/host-set/hosts.hbs +++ b/ui/admin/app/templates/scopes/scope/host-catalogs/host-catalog/host-sets/host-set/hosts.hbs @@ -1,6 +1,7 @@ {{page-title (t 'resources.host.title_plural')}} {{#if @model.hosts}} + @@ -79,4 +80,4 @@ --}} -{{/unless}} \ No newline at end of file +{{/unless}} From 449181390e575474be93e66b1198f36dd0d2bede Mon Sep 17 00:00:00 2001 From: dharini Date: Thu, 10 Feb 2022 18:44:40 -0800 Subject: [PATCH 5/6] lint --- .../host-catalogs/host-catalog/host-sets/host-set/hosts.hbs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ui/admin/app/templates/scopes/scope/host-catalogs/host-catalog/host-sets/host-set/hosts.hbs b/ui/admin/app/templates/scopes/scope/host-catalogs/host-catalog/host-sets/host-set/hosts.hbs index d78229fe4..9bcbe0fd4 100644 --- a/ui/admin/app/templates/scopes/scope/host-catalogs/host-catalog/host-sets/host-set/hosts.hbs +++ b/ui/admin/app/templates/scopes/scope/host-catalogs/host-catalog/host-sets/host-set/hosts.hbs @@ -80,4 +80,4 @@ --}} -{{/unless}} +{{/unless}} \ No newline at end of file From 8546275249fa28419ce5225070992c1d35995b11 Mon Sep 17 00:00:00 2001 From: Carlos Alcaide Corvo Date: Fri, 11 Feb 2022 08:51:22 -0800 Subject: [PATCH 6/6] =?UTF-8?q?fix:=20=F0=9F=90=9B=20Fix=20filter=20field?= =?UTF-8?q?=20for=20host-set=20in=20mirage?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Fix the filter field for host-set in mirage. It was returning an error rather than a string. --- addons/api/mirage/factories/host-set.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/addons/api/mirage/factories/host-set.js b/addons/api/mirage/factories/host-set.js index 038bf6a7c..979d5c996 100644 --- a/addons/api/mirage/factories/host-set.js +++ b/addons/api/mirage/factories/host-set.js @@ -43,7 +43,7 @@ export default factory.extend({ // Azure specific filter() { if (this.plugin?.name === 'azure') { - return `${database.column}=${database.collation}`; + return `${database.column()}=${database.collation()}`; } }, });