Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Enabling keyword preservation for wider array of resources #864

Merged
merged 9 commits into from
Nov 22, 2023
38 changes: 21 additions & 17 deletions src/keywordPreservation.ts
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ export const doesHaveKeywordMarker = (
export const getPreservableFieldsFromAssets = (
asset: object,
keywordMappings: KeywordMappings,
resourceSpecificIdentifiers: Partial<{ [key in AssetTypes]: string | string[] }>,
resourceSpecificIdentifiers: Partial<Record<AssetTypes, string | string[]>>,
address = ''
): string[] => {
if (typeof asset === 'string') {
Expand All @@ -41,20 +41,26 @@ export const getPreservableFieldsFromAssets = (
return asset
.map((arrayItem) => {
const resourceIdentifiers: string[] = (() => {
const identifiers = resourceSpecificIdentifiers[address];
if (Array.isArray(identifiers)) {
return identifiers;
const identifierOrIdentifiers = resourceSpecificIdentifiers[address as AssetTypes];

if (Array.isArray(identifierOrIdentifiers)) {
return identifierOrIdentifiers;
}

if (identifierOrIdentifiers === undefined) {
return [];
}
return [identifiers];

return [identifierOrIdentifiers];
})();

const specificAddress = resourceIdentifiers.reduce(
(aggregateAddress, resourceIdentifier) => {
resourceSpecificIdentifiers[address];
if (resourceIdentifier === undefined) return null; // See if this specific resource type has an identifier
if (resourceIdentifier === undefined) return ''; // See if this specific resource type has an identifier

const identifierFieldValue = arrayItem[resourceIdentifier];
if (identifierFieldValue === undefined) return null; // See if this specific array item possess the resource-specific identifier
if (identifierFieldValue === undefined) return ''; // See if this specific array item possess the resource-specific identifier

if (aggregateAddress === '') {
return `${resourceIdentifier}=${identifierFieldValue}`;
Expand All @@ -65,7 +71,7 @@ export const getPreservableFieldsFromAssets = (
''
);

if (specificAddress === null) {
if (specificAddress.length === 0) {
return [];
}

Expand Down Expand Up @@ -227,15 +233,13 @@ export const preserveKeywords = ({
}): object => {
if (Object.keys(keywordMappings).length === 0) return remoteAssets;

const resourceSpecificIdentifiers: Partial<{ [key in AssetTypes]: string[] }> =
auth0Handlers.reduce((acc, handler): Partial<{ [key in AssetTypes]: string[] }> => {
return {
...acc,
[handler.type]: handler.identifiers.filter((identifiers) => {
return identifiers !== handler.id;
})[0],
};
}, {});
const resourceSpecificIdentifiers: Partial<Record<AssetTypes, string[]>> = auth0Handlers.reduce(
(acc, handler) => {
acc[handler.type] = handler.identifiers.flat();
return acc;
},
{}
);

const addresses = getPreservableFieldsFromAssets(
localAssets,
Expand Down
83 changes: 82 additions & 1 deletion test/keywordPreservation.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -494,6 +494,22 @@ describe('preserveKeywords', () => {
status: 'ready',
},
],
guardianFactorProviders: [
{
name: 'sms',
auth_token: '##AUTH_TOKEN##',
from: '##COMPANY_NAME##',
sid: '##TWILIO_SID##',
messaging_service_sid: '##TWILIO_SID##',
provider: 'twilio',
},
],
pages: [
{
name: 'error_page',
url: '##URL##/error',
},
],
};

const mockRemoteAssets = {
Expand All @@ -505,7 +521,6 @@ describe('preserveKeywords', () => {
universal_login_enabled: true,
customText: {},
},
pages: undefined, //TODO: test these cases more thoroughly
rules: null, //TODO: test these cases more thoroughly
connections: [], // Empty on remote but has local assets
actions: [
Expand Down Expand Up @@ -537,6 +552,22 @@ describe('preserveKeywords', () => {
status: 'ready',
},
],
guardianFactorProviders: [
{
name: 'sms',
auth_token: 'mock-twilio-auth-token',
from: 'travel0',
sid: 'twilio-sid',
messaging_service_sid: 'twilio-sid',
provider: 'twilio',
},
],
pages: [
{
name: 'error_page',
url: 'https://travel0.com/error',
},
],
};

const auth0Handlers = [
Expand All @@ -561,6 +592,8 @@ describe('preserveKeywords', () => {
type: 'resourceServers',
},
{ id: 'id', identifiers: ['id', 'domain'], type: 'customDomains' },
{ id: 'name', identifiers: ['id', 'name'], type: 'guardianFactorProviders' },
{ id: 'id', identifiers: ['name'], type: 'pages' },
];

it('should preserve keywords when they correlate to keyword mappings', () => {
Expand All @@ -569,9 +602,12 @@ describe('preserveKeywords', () => {
remoteAssets: mockRemoteAssets,
keywordMappings: {
COMPANY_NAME: 'Travel0',
URL: 'https://trave0.com',
ALLOWED_LOGOUT_URLS: ['localhost:3000/logout', 'https://travel0.com/logout'],
ENV: 'Production',
API_MAIN_IDENTIFIER: 'https://travel0.com/api/v1',
AUTH_TOKEN: 'mock-twilio-auth-token',
TWILIO_SID: 'twilio-sid',
},
auth0Handlers,
});
Expand All @@ -590,6 +626,11 @@ describe('preserveKeywords', () => {
},
];
expected.customDomains[0].domain = '##COMPANY_NAME##.com';
expected.guardianFactorProviders[0].sid = '##TWILIO_SID##';
expected.guardianFactorProviders[0].messaging_service_sid = '##TWILIO_SID##';
expected.guardianFactorProviders[0].auth_token = '##AUTH_TOKEN##';
expected.guardianFactorProviders[0].from = '##COMPANY_NAME##';
expected.pages[0].url = '##URL##/error';
return expected;
})()
);
Expand Down Expand Up @@ -883,4 +924,44 @@ describe('preserveKeywords', () => {
connections: null,
});
});

it('`guardianFactorProviders` should have fields preserved', () => {
const preservedAssets = preserveKeywords({
localAssets: {
guardianFactorProviders: [
{
auth_token: '##AUTH_TOKEN##',
name: 'sms',
},
],
},
remoteAssets: {
guardianFactorProviders: [
{
auth_token: 'auth_token',
name: 'sms',
},
],
},
keywordMappings: {
AUTH_TOKEN: 'auth_token',
},
auth0Handlers: [
{
id: 'name',
identifiers: ['id', 'name'],
type: 'guardianFactorProviders',
},
],
});

expect(preservedAssets).to.deep.equal({
guardianFactorProviders: [
{
auth_token: '##AUTH_TOKEN##',
name: 'sms',
},
],
});
});
});