chore(shared-cms): strapi 5 upgrade

Because:

- We want to use Strapi 5

This commit:

- Upgrades our queries and libraries to use Strapi 5

Closes FXA-10454
This commit is contained in:
julianpoyourow 2024-10-07 17:31:51 +00:00
Родитель a2e3ee8ead
Коммит b32169036f
Не найден ключ, соответствующий данной подписи
Идентификатор ключа GPG: EA0570ABC73D47D3
59 изменённых файлов: 1760 добавлений и 6064 удалений

Просмотреть файл

@ -4,5 +4,6 @@
# Autogenerated files
packages/fxa-admin-server/src/schema.gql
packages/fxa-admin-server/src/graphql.ts
libs/shared/cms/src/__generated__/**/*
/.nx/workspace-data
/.nx/workspace-data

Просмотреть файл

@ -71,10 +71,8 @@ export default async function RootLayout({
/>
}
purchaseDetails={
cms.defaultPurchase.data.attributes.purchaseDetails.data.attributes.localizations.data.at(
0
)?.attributes ||
cms.defaultPurchase.data.attributes.purchaseDetails.data.attributes
cms.defaultPurchase.purchaseDetails.localizations.at(0) ||
cms.defaultPurchase.purchaseDetails
}
>
<Details
@ -82,11 +80,8 @@ export default async function RootLayout({
interval={cart.interval}
invoice={cart.invoicePreview}
purchaseDetails={
cms.defaultPurchase.data.attributes.purchaseDetails.data.attributes.localizations.data.at(
0
)?.attributes ||
cms.defaultPurchase.data.attributes.purchaseDetails.data
.attributes
cms.defaultPurchase.purchaseDetails.localizations.at(0) ||
cms.defaultPurchase.purchaseDetails
}
/>
</PurchaseDetails>
@ -103,13 +98,9 @@ export default async function RootLayout({
<TermsAndPrivacy
l10n={l10n}
{...cart}
{...(cms.commonContent.data.attributes.localizations.data.at(0)
?.attributes || cms.commonContent.data.attributes)}
{...(cms.defaultPurchase.data.attributes.purchaseDetails.data.attributes.localizations.data.at(
0
)?.attributes ||
cms.defaultPurchase.data.attributes.purchaseDetails.data
.attributes)}
{...(cms.commonContent.localizations.at(0) || cms.commonContent)}
{...(cms.defaultPurchase.purchaseDetails.localizations.at(0) ||
cms.defaultPurchase.purchaseDetails)}
contentServerUrl={config.contentServerUrl}
showFXALinks={true}
/>

Просмотреть файл

@ -75,13 +75,10 @@ export default async function CheckoutSuccess({
]);
const { productName } =
cms.defaultPurchase.data.attributes.purchaseDetails.data.attributes.localizations.data.at(
0
)?.attributes ||
cms.defaultPurchase.data.attributes.purchaseDetails.data.attributes;
cms.defaultPurchase.purchaseDetails.localizations.at(0) ||
cms.defaultPurchase.purchaseDetails;
const { successActionButtonUrl, successActionButtonLabel } =
cms.commonContent.data.attributes.localizations.data.at(0)?.attributes ||
cms.commonContent.data.attributes;
cms.commonContent.localizations.at(0) || cms.commonContent;
return (
<>

Просмотреть файл

@ -21,7 +21,6 @@ import {
ServicesWithCapabilitiesResult,
StrapiClient,
MockStrapiClientConfigProvider,
StrapiEntityFactory,
} from '@fxa/shared/cms';
import { MockFirestoreProvider } from '@fxa/shared/db/firestore';
import { MockStatsDProvider } from '@fxa/shared/metrics/statsd';
@ -53,39 +52,21 @@ describe('CapabilityManager', () => {
describe('getClients', () => {
it('should return services with capabilities', async () => {
const clientResults = [
StrapiEntityFactory(
ServiceResultFactory({
oauthClientId: 'client1',
capabilities: {
data: [
StrapiEntityFactory(
CapabilitiesResultFactory({ slug: 'exampleCap8' })
),
StrapiEntityFactory(
CapabilitiesResultFactory({ slug: 'exampleCap0' })
),
StrapiEntityFactory(
CapabilitiesResultFactory({ slug: 'exampleCap2' })
),
StrapiEntityFactory(
CapabilitiesResultFactory({ slug: 'exampleCap4' })
),
StrapiEntityFactory(
CapabilitiesResultFactory({ slug: 'exampleCap5' })
),
StrapiEntityFactory(
CapabilitiesResultFactory({ slug: 'exampleCap6' })
),
],
},
})
),
ServiceResultFactory({
oauthClientId: 'client1',
capabilities: [
CapabilitiesResultFactory({ slug: 'exampleCap8' }),
CapabilitiesResultFactory({ slug: 'exampleCap0' }),
CapabilitiesResultFactory({ slug: 'exampleCap2' }),
CapabilitiesResultFactory({ slug: 'exampleCap4' }),
CapabilitiesResultFactory({ slug: 'exampleCap5' }),
CapabilitiesResultFactory({ slug: 'exampleCap6' }),
],
}),
];
const mockServicesWithCapabilitiesQuery =
ServicesWithCapabilitiesQueryFactory({
services: {
data: clientResults,
},
services: clientResults,
});
jest
.spyOn(productConfigurationManager, 'getServicesWithCapabilities')
@ -99,8 +80,8 @@ describe('CapabilityManager', () => {
expect(result.length).toBe(1);
expect(result.at(0)?.clientId).toBe('client1');
const actualCapabilities = clientResults[0].attributes.capabilities.data
.map((capability) => capability.attributes.slug)
const actualCapabilities = clientResults[0].capabilities
.map((capability) => capability.slug)
.sort();
expect(result.at(0)?.capabilities).toHaveLength(6);
@ -118,9 +99,9 @@ describe('CapabilityManager', () => {
'getPurchaseDetailsForCapabilityServiceByPlanIds'
)
.mockResolvedValue(
new CapabilityServiceByPlanIdsResultUtil([
mockCapabilityServiceByPlanIdsQuery,
] as CapabilityServiceByPlanIdsResult[])
new CapabilityServiceByPlanIdsResultUtil(
mockCapabilityServiceByPlanIdsQuery as CapabilityServiceByPlanIdsResult
)
);
const result = await capabilityManager.priceIdsToClientCapabilities([
'planId1',
@ -129,30 +110,15 @@ describe('CapabilityManager', () => {
});
it('should return empty results when there are no capability collection items', async () => {
const mockCapabilityOfferingResult = StrapiEntityFactory(
CapabilityOfferingResultFactory({
capabilities: {
data: [],
},
})
);
const mockCapabilityPurchaseResult = StrapiEntityFactory(
CapabilityPurchaseResultFactory({
offering: {
data: mockCapabilityOfferingResult,
},
})
);
const mockCapabilityOfferingResult = CapabilityOfferingResultFactory({
capabilities: [],
});
const mockCapabilityPurchaseResult = CapabilityPurchaseResultFactory({
offering: mockCapabilityOfferingResult,
});
const mockCapabilityServiceByPlanIdsQuery =
CapabilityServiceByPlanIdsQueryFactory({
purchases: {
meta: {
pagination: {
total: 1,
},
},
data: [mockCapabilityPurchaseResult],
},
purchases: [mockCapabilityPurchaseResult],
});
jest
.spyOn(
@ -160,9 +126,9 @@ describe('CapabilityManager', () => {
'getPurchaseDetailsForCapabilityServiceByPlanIds'
)
.mockResolvedValue(
new CapabilityServiceByPlanIdsResultUtil([
mockCapabilityServiceByPlanIdsQuery,
] as CapabilityServiceByPlanIdsResult[])
new CapabilityServiceByPlanIdsResultUtil(
mockCapabilityServiceByPlanIdsQuery as CapabilityServiceByPlanIdsResult
)
);
const result = await capabilityManager.priceIdsToClientCapabilities([
@ -172,39 +138,20 @@ describe('CapabilityManager', () => {
});
it('should return empty results when there are no service collection items', async () => {
const mockCapabilityOfferingResult = StrapiEntityFactory(
CapabilityOfferingResultFactory({
capabilities: {
data: [
StrapiEntityFactory(
CapabilityCapabilitiesResultFactory({
slug: 'slug1',
services: {
data: [],
},
})
),
],
},
})
);
const mockCapabilityPurchaseResult = StrapiEntityFactory(
CapabilityPurchaseResultFactory({
offering: {
data: mockCapabilityOfferingResult,
},
})
);
const mockCapabilityOfferingResult = CapabilityOfferingResultFactory({
capabilities: [
CapabilityCapabilitiesResultFactory({
slug: 'slug1',
services: [],
}),
],
});
const mockCapabilityPurchaseResult = CapabilityPurchaseResultFactory({
offering: mockCapabilityOfferingResult,
});
const mockCapabilityServiceByPlanIdsQuery =
CapabilityServiceByPlanIdsQueryFactory({
purchases: {
meta: {
pagination: {
total: 1,
},
},
data: [mockCapabilityPurchaseResult],
},
purchases: [mockCapabilityPurchaseResult],
});
jest
.spyOn(
@ -212,9 +159,9 @@ describe('CapabilityManager', () => {
'getPurchaseDetailsForCapabilityServiceByPlanIds'
)
.mockResolvedValue(
new CapabilityServiceByPlanIdsResultUtil([
mockCapabilityServiceByPlanIdsQuery,
] as CapabilityServiceByPlanIdsResult[])
new CapabilityServiceByPlanIdsResultUtil(
mockCapabilityServiceByPlanIdsQuery as CapabilityServiceByPlanIdsResult
)
);
const result = await capabilityManager.priceIdsToClientCapabilities([
@ -224,74 +171,41 @@ describe('CapabilityManager', () => {
});
it('should return planIds to client capabilities', async () => {
const mockCapabilityOfferingResult = StrapiEntityFactory(
CapabilityOfferingResultFactory({
capabilities: {
data: [
StrapiEntityFactory(
CapabilityCapabilitiesResultFactory({
slug: 'slug1',
services: {
data: [
StrapiEntityFactory(
CapabilityServicesResultFactory({
oauthClientId: 'clientId1',
})
),
],
},
})
),
StrapiEntityFactory(
CapabilityCapabilitiesResultFactory({
slug: 'slug2a',
services: {
data: [
StrapiEntityFactory(
CapabilityServicesResultFactory({
oauthClientId: 'clientId2',
})
),
],
},
})
),
StrapiEntityFactory(
CapabilityCapabilitiesResultFactory({
slug: 'slug2b',
services: {
data: [
StrapiEntityFactory(
CapabilityServicesResultFactory({
oauthClientId: 'clientId2',
})
),
],
},
})
),
const mockCapabilityOfferingResult = CapabilityOfferingResultFactory({
capabilities: [
CapabilityCapabilitiesResultFactory({
slug: 'slug1',
services: [
CapabilityServicesResultFactory({
oauthClientId: 'clientId1',
}),
],
},
})
);
const mockCapabilityPurchaseResult = StrapiEntityFactory(
CapabilityPurchaseResultFactory({
stripePlanChoices: [{ stripePlanChoice: 'planId1' }],
offering: {
data: mockCapabilityOfferingResult,
},
})
);
}),
CapabilityCapabilitiesResultFactory({
slug: 'slug2a',
services: [
CapabilityServicesResultFactory({
oauthClientId: 'clientId2',
}),
],
}),
CapabilityCapabilitiesResultFactory({
slug: 'slug2b',
services: [
CapabilityServicesResultFactory({
oauthClientId: 'clientId2',
}),
],
}),
],
});
const mockCapabilityPurchaseResult = CapabilityPurchaseResultFactory({
stripePlanChoices: [{ stripePlanChoice: 'planId1' }],
offering: mockCapabilityOfferingResult,
});
const mockCapabilityServiceByPlanIdsQuery =
CapabilityServiceByPlanIdsQueryFactory({
purchases: {
meta: {
pagination: {
total: 1,
},
},
data: [mockCapabilityPurchaseResult],
},
purchases: [mockCapabilityPurchaseResult],
});
jest
.spyOn(
@ -299,9 +213,9 @@ describe('CapabilityManager', () => {
'getPurchaseDetailsForCapabilityServiceByPlanIds'
)
.mockResolvedValue(
new CapabilityServiceByPlanIdsResultUtil([
mockCapabilityServiceByPlanIdsQuery,
] as CapabilityServiceByPlanIdsResult[])
new CapabilityServiceByPlanIdsResultUtil(
mockCapabilityServiceByPlanIdsQuery as CapabilityServiceByPlanIdsResult
)
);
const result = await capabilityManager.priceIdsToClientCapabilities([

Просмотреть файл

@ -17,8 +17,8 @@ export class CapabilityManager {
).getServices();
return clients.map((client: ServiceResult) => {
const capabilities = client.capabilities.data.map(
(capability) => capability.attributes.slug
const capabilities = client.capabilities.map(
(capability) => capability.slug
);
const sortedCapabilities = capabilities.sort();
return {
@ -50,20 +50,16 @@ export class CapabilityManager {
purchaseDetails.capabilityOfferingForPlanId(subscribedPrice);
// continue if neither offering nor capabilities exist
if (!capabilityOffering || !capabilityOffering?.capabilities?.data)
continue;
if (!capabilityOffering || !capabilityOffering?.capabilities) continue;
for (const capabilityCollection of capabilityOffering.capabilities.data) {
for (const capabilityCollection of capabilityOffering.capabilities) {
// continue if individual capability does not contain any services
if (!capabilityCollection.attributes.services.data) continue;
if (!capabilityCollection.services) continue;
for (const capability of capabilityCollection.attributes.services
.data) {
result[capability.attributes.oauthClientId] ||= [];
for (const capability of capabilityCollection.services) {
result[capability.oauthClientId] ||= [];
result[capability.attributes.oauthClientId].push(
capabilityCollection.attributes.slug
);
result[capability.oauthClientId].push(capabilityCollection.slug);
}
}
}

Просмотреть файл

@ -24,7 +24,6 @@ import {
MockStrapiClientConfigProvider,
ProductConfigurationManager,
StrapiClient,
StrapiEntityFactory,
} from '@fxa/shared/cms';
import { CartEligibilityStatus } from '@fxa/shared/db/mysql/account';
@ -66,9 +65,9 @@ describe('EligibilityManager', () => {
jest
.spyOn(productConfigurationManager, 'getPurchaseDetailsForEligibility')
.mockResolvedValue(
new EligibilityContentByPlanIdsResultUtil([
EligibilityContentByPlanIdsResultFactory(),
])
new EligibilityContentByPlanIdsResultUtil(
EligibilityContentByPlanIdsResultFactory()
)
);
const result = await manager.getOfferingOverlap(['test'], [], 'test');
@ -77,7 +76,7 @@ describe('EligibilityManager', () => {
it('should return same offeringStripeProductIds as same comparison', async () => {
const eligibilityContentByPlanIdsResultUtil =
new EligibilityContentByPlanIdsResultUtil([]);
new EligibilityContentByPlanIdsResultUtil({ purchases: [] });
jest
.spyOn(productConfigurationManager, 'getPurchaseDetailsForEligibility')
.mockResolvedValue(eligibilityContentByPlanIdsResultUtil);
@ -100,39 +99,27 @@ describe('EligibilityManager', () => {
it('should return subgroup upgrade target offeringStripeProductIds as upgrade comparison', async () => {
const mockOfferingResult = EligibilityOfferingResultFactory({
stripeProductId: 'prod_test3',
subGroups: {
data: [
StrapiEntityFactory(
EligibilitySubgroupResultFactory({
offerings: {
data: [
StrapiEntityFactory(
EligibilitySubgroupOfferingResultFactory({
stripeProductId: 'prod_test',
countries: ['usa'],
})
),
StrapiEntityFactory(
EligibilitySubgroupOfferingResultFactory({
stripeProductId: 'prod_test2',
countries: ['usa'],
})
),
StrapiEntityFactory(
EligibilitySubgroupOfferingResultFactory({
stripeProductId: 'prod_test3',
countries: ['usa'],
})
),
],
},
})
),
],
},
subGroups: [
EligibilitySubgroupResultFactory({
offerings: [
EligibilitySubgroupOfferingResultFactory({
stripeProductId: 'prod_test',
countries: ['usa'],
}),
EligibilitySubgroupOfferingResultFactory({
stripeProductId: 'prod_test2',
countries: ['usa'],
}),
EligibilitySubgroupOfferingResultFactory({
stripeProductId: 'prod_test3',
countries: ['usa'],
}),
],
}),
],
});
const eligibilityContentByPlanIdsResultUtil =
new EligibilityContentByPlanIdsResultUtil([]);
new EligibilityContentByPlanIdsResultUtil({ purchases: [] });
jest
.spyOn(productConfigurationManager, 'getPurchaseDetailsForEligibility')
.mockResolvedValue(eligibilityContentByPlanIdsResultUtil);
@ -152,33 +139,23 @@ describe('EligibilityManager', () => {
it('should return subgroup downgrade target offeringStripeProductIds as downgrade comparison', async () => {
const mockOfferingResult = EligibilityOfferingResultFactory({
stripeProductId: 'prod_test',
subGroups: {
data: [
StrapiEntityFactory(
EligibilitySubgroupResultFactory({
offerings: {
data: [
StrapiEntityFactory(
EligibilitySubgroupOfferingResultFactory({
stripeProductId: 'prod_test',
countries: ['usa'],
})
),
StrapiEntityFactory(
EligibilitySubgroupOfferingResultFactory({
stripeProductId: 'prod_test2',
countries: ['usa'],
})
),
],
},
})
),
],
},
subGroups: [
EligibilitySubgroupResultFactory({
offerings: [
EligibilitySubgroupOfferingResultFactory({
stripeProductId: 'prod_test',
countries: ['usa'],
}),
EligibilitySubgroupOfferingResultFactory({
stripeProductId: 'prod_test2',
countries: ['usa'],
}),
],
}),
],
});
const eligibilityContentByPlanIdsResultUtil =
new EligibilityContentByPlanIdsResultUtil([]);
new EligibilityContentByPlanIdsResultUtil({ purchases: [] });
jest
.spyOn(productConfigurationManager, 'getPurchaseDetailsForEligibility')
.mockResolvedValue(eligibilityContentByPlanIdsResultUtil);
@ -203,7 +180,7 @@ describe('EligibilityManager', () => {
stripeProductId: 'prod_test',
});
const eligibilityContentByPlanIdsResultUtil =
new EligibilityContentByPlanIdsResultUtil([]);
new EligibilityContentByPlanIdsResultUtil({ purchases: [] });
jest
.spyOn(productConfigurationManager, 'getPurchaseDetailsForEligibility')
.mockResolvedValue(eligibilityContentByPlanIdsResultUtil);
@ -224,36 +201,26 @@ describe('EligibilityManager', () => {
it('should return upgrade comparison for upgrade priceId', async () => {
const mockOfferingResult = EligibilityOfferingResultFactory({
stripeProductId: 'prod_test2',
subGroups: {
data: [
StrapiEntityFactory(
EligibilitySubgroupResultFactory({
offerings: {
data: [
StrapiEntityFactory(
EligibilitySubgroupOfferingResultFactory({
stripeProductId: 'prod_test',
countries: ['usa'],
})
),
StrapiEntityFactory(
EligibilitySubgroupOfferingResultFactory({
stripeProductId: 'prod_test2',
countries: ['usa'],
})
),
],
},
})
),
],
},
subGroups: [
EligibilitySubgroupResultFactory({
offerings: [
EligibilitySubgroupOfferingResultFactory({
stripeProductId: 'prod_test',
countries: ['usa'],
}),
EligibilitySubgroupOfferingResultFactory({
stripeProductId: 'prod_test2',
countries: ['usa'],
}),
],
}),
],
});
const existingResult = EligibilityOfferingResultFactory({
stripeProductId: 'prod_test',
});
const eligibilityContentByPlanIdsResultUtil =
new EligibilityContentByPlanIdsResultUtil([]);
new EligibilityContentByPlanIdsResultUtil({ purchases: [] });
jest
.spyOn(productConfigurationManager, 'getPurchaseDetailsForEligibility')
.mockResolvedValue(eligibilityContentByPlanIdsResultUtil);
@ -274,62 +241,42 @@ describe('EligibilityManager', () => {
it('should return multiple comparisons in multiple subgroups', async () => {
const mockOfferingResult = EligibilityOfferingResultFactory({
stripeProductId: 'prod_test2',
subGroups: {
data: [
StrapiEntityFactory(
EligibilitySubgroupResultFactory({
offerings: {
data: [
StrapiEntityFactory(
EligibilitySubgroupOfferingResultFactory({
stripeProductId: 'prod_test',
countries: ['usa'],
})
),
StrapiEntityFactory(
EligibilitySubgroupOfferingResultFactory({
stripeProductId: 'prod_test2',
countries: ['usa'],
})
),
StrapiEntityFactory(
EligibilitySubgroupOfferingResultFactory({
stripeProductId: 'prod_test3',
countries: ['usa'],
})
),
],
},
})
),
StrapiEntityFactory(
EligibilitySubgroupResultFactory({
offerings: {
data: [
StrapiEntityFactory(
EligibilitySubgroupOfferingResultFactory({
stripeProductId: 'prod_test',
countries: ['usa'],
})
),
StrapiEntityFactory(
EligibilitySubgroupOfferingResultFactory({
stripeProductId: 'prod_test2',
countries: ['usa'],
})
),
],
},
})
),
],
},
subGroups: [
EligibilitySubgroupResultFactory({
offerings: [
EligibilitySubgroupOfferingResultFactory({
stripeProductId: 'prod_test',
countries: ['usa'],
}),
EligibilitySubgroupOfferingResultFactory({
stripeProductId: 'prod_test2',
countries: ['usa'],
}),
EligibilitySubgroupOfferingResultFactory({
stripeProductId: 'prod_test3',
countries: ['usa'],
}),
],
}),
EligibilitySubgroupResultFactory({
offerings: [
EligibilitySubgroupOfferingResultFactory({
stripeProductId: 'prod_test',
countries: ['usa'],
}),
EligibilitySubgroupOfferingResultFactory({
stripeProductId: 'prod_test2',
countries: ['usa'],
}),
],
}),
],
});
const existingResult = EligibilityOfferingResultFactory({
stripeProductId: 'prod_test',
});
const eligibilityContentByPlanIdsResultUtil =
new EligibilityContentByPlanIdsResultUtil([]);
new EligibilityContentByPlanIdsResultUtil({ purchases: [] });
jest
.spyOn(productConfigurationManager, 'getPurchaseDetailsForEligibility')
.mockResolvedValue(eligibilityContentByPlanIdsResultUtil);
@ -385,33 +332,21 @@ describe('EligibilityManager', () => {
it('should return subgroup upgrade target offeringStripeProductIds as upgrade comparison', async () => {
const mockTargetOfferingResult = EligibilityContentOfferingResultFactory({
stripeProductId: 'prod_test3',
subGroups: {
data: [
StrapiEntityFactory(
EligibilityContentSubgroupResultFactory({
offerings: {
data: [
StrapiEntityFactory(
EligibilityContentSubgroupOfferingResultFactory({
stripeProductId: 'prod_test',
})
),
StrapiEntityFactory(
EligibilityContentSubgroupOfferingResultFactory({
stripeProductId: 'prod_test2',
})
),
StrapiEntityFactory(
EligibilityContentSubgroupOfferingResultFactory({
stripeProductId: 'prod_test3',
})
),
],
},
})
),
],
},
subGroups: [
EligibilityContentSubgroupResultFactory({
offerings: [
EligibilityContentSubgroupOfferingResultFactory({
stripeProductId: 'prod_test',
}),
EligibilityContentSubgroupOfferingResultFactory({
stripeProductId: 'prod_test2',
}),
EligibilityContentSubgroupOfferingResultFactory({
stripeProductId: 'prod_test3',
}),
],
}),
],
});
const result = manager.getProductIdOverlap(
@ -425,28 +360,18 @@ describe('EligibilityManager', () => {
it('should return subgroup downgrade target offeringStripeProductIds as downgrade comparison', async () => {
const mockTargetOfferingResult = EligibilityContentOfferingResultFactory({
stripeProductId: 'prod_test',
subGroups: {
data: [
StrapiEntityFactory(
EligibilityContentSubgroupResultFactory({
offerings: {
data: [
StrapiEntityFactory(
EligibilityContentSubgroupOfferingResultFactory({
stripeProductId: 'prod_test',
})
),
StrapiEntityFactory(
EligibilityContentSubgroupOfferingResultFactory({
stripeProductId: 'prod_test2',
})
),
],
},
})
),
],
},
subGroups: [
EligibilityContentSubgroupResultFactory({
offerings: [
EligibilityContentSubgroupOfferingResultFactory({
stripeProductId: 'prod_test',
}),
EligibilityContentSubgroupOfferingResultFactory({
stripeProductId: 'prod_test2',
}),
],
}),
],
});
const result = manager.getProductIdOverlap(
@ -473,28 +398,18 @@ describe('EligibilityManager', () => {
it('should return upgrade comparison for upgrade priceId', async () => {
const mockTargetOfferingResult = EligibilityContentOfferingResultFactory({
stripeProductId: 'prod_test2',
subGroups: {
data: [
StrapiEntityFactory(
EligibilityContentSubgroupResultFactory({
offerings: {
data: [
StrapiEntityFactory(
EligibilityContentSubgroupOfferingResultFactory({
stripeProductId: 'prod_test',
})
),
StrapiEntityFactory(
EligibilityContentSubgroupOfferingResultFactory({
stripeProductId: 'prod_test2',
})
),
],
},
})
),
],
},
subGroups: [
EligibilityContentSubgroupResultFactory({
offerings: [
EligibilityContentSubgroupOfferingResultFactory({
stripeProductId: 'prod_test',
}),
EligibilityContentSubgroupOfferingResultFactory({
stripeProductId: 'prod_test2',
}),
],
}),
],
});
const result = manager.getProductIdOverlap(
['prod_test'],
@ -507,51 +422,31 @@ describe('EligibilityManager', () => {
it('should return multiple comparisons in multiple subgroups', async () => {
const mockTargetOfferingResult = EligibilityContentOfferingResultFactory({
stripeProductId: 'prod_test2',
subGroups: {
data: [
StrapiEntityFactory(
EligibilityContentSubgroupResultFactory({
offerings: {
data: [
StrapiEntityFactory(
EligibilityContentSubgroupOfferingResultFactory({
stripeProductId: 'prod_test',
})
),
StrapiEntityFactory(
EligibilityContentSubgroupOfferingResultFactory({
stripeProductId: 'prod_test2',
})
),
StrapiEntityFactory(
EligibilityContentSubgroupOfferingResultFactory({
stripeProductId: 'prod_test3',
})
),
],
},
})
),
StrapiEntityFactory(
EligibilityContentSubgroupResultFactory({
offerings: {
data: [
StrapiEntityFactory(
EligibilityContentSubgroupOfferingResultFactory({
stripeProductId: 'prod_test',
})
),
StrapiEntityFactory(
EligibilityContentSubgroupOfferingResultFactory({
stripeProductId: 'prod_test2',
})
),
],
},
})
),
],
},
subGroups: [
EligibilityContentSubgroupResultFactory({
offerings: [
EligibilityContentSubgroupOfferingResultFactory({
stripeProductId: 'prod_test',
}),
EligibilityContentSubgroupOfferingResultFactory({
stripeProductId: 'prod_test2',
}),
EligibilityContentSubgroupOfferingResultFactory({
stripeProductId: 'prod_test3',
}),
],
}),
EligibilityContentSubgroupResultFactory({
offerings: [
EligibilityContentSubgroupOfferingResultFactory({
stripeProductId: 'prod_test',
}),
EligibilityContentSubgroupOfferingResultFactory({
stripeProductId: 'prod_test2',
}),
],
}),
],
});
const result = manager.getProductIdOverlap(
['prod_test2', 'prod_test3'],

Просмотреть файл

@ -112,8 +112,7 @@ export class EligibilityManager {
if (overlap.comparison === OfferingComparison.DOWNGRADE)
return EligibilityStatus.DOWNGRADE;
const targetPriceIds =
targetOffering.defaultPurchase.data.attributes.stripePlanChoices;
const targetPriceIds = targetOffering.defaultPurchase.stripePlanChoices;
const targetPrice = await this.priceManager.retrieveByInterval(
targetPriceIds.map((el) => el.stripePlanChoice),
interval

Просмотреть файл

@ -20,7 +20,6 @@ import {
MockStrapiClientConfigProvider,
ProductConfigurationManager,
StrapiClient,
StrapiEntityFactory,
} from '@fxa/shared/cms';
import { MockFirestoreProvider } from '@fxa/shared/db/firestore';
import { MockStatsDProvider } from '@fxa/shared/metrics/statsd';
@ -84,7 +83,7 @@ describe('EligibilityService', () => {
.mockResolvedValue(
new EligibilityContentByOfferingResultUtil(
EligibilityContentByOfferingResultFactory({
offerings: { data: [] },
offerings: [],
})
)
);
@ -115,9 +114,7 @@ describe('EligibilityService', () => {
.mockResolvedValue(
new EligibilityContentByOfferingResultUtil(
EligibilityContentByOfferingResultFactory({
offerings: {
data: [StrapiEntityFactory(mockOffering)],
},
offerings: [mockOffering],
})
)
);

Просмотреть файл

@ -24,15 +24,15 @@ export const offeringComparison = (
) => {
if (targetOffering.stripeProductId === fromOfferingProductId)
return OfferingComparison.SAME;
const commonSubgroups = targetOffering.subGroups.data.filter(
const commonSubgroups = targetOffering.subGroups.filter(
(subgroup) =>
!!subgroup.attributes.offerings.data.find(
(oc) => oc.attributes.stripeProductId === fromOfferingProductId
!!subgroup.offerings.find(
(oc) => oc.stripeProductId === fromOfferingProductId
)
);
if (!commonSubgroups.length) return null;
const subgroupProductIds = commonSubgroups[0].attributes.offerings.data.map(
(o) => o.attributes.stripeProductId
const subgroupProductIds = commonSubgroups[0].offerings.map(
(o) => o.stripeProductId
);
const existingIndex = subgroupProductIds.indexOf(fromOfferingProductId);
const targetIndex = subgroupProductIds.indexOf(

Просмотреть файл

@ -19,7 +19,6 @@ import {
PurchaseDetailsTransformedFactory,
StrapiClient,
MockStrapiClientConfigProvider,
StrapiEntityFactory,
} from '@fxa/shared/cms';
import { MockFirestoreProvider } from '@fxa/shared/db/firestore';
import { MockStatsDProvider } from '@fxa/shared/metrics/statsd';
@ -149,7 +148,7 @@ describe('StripeMapperService', () => {
it('should return data from cms default locale if no localization data is available', async () => {
const expected = PurchaseWithDetailsOfferingContentTransformedFactory();
expected.purchaseDetails.data.attributes.localizations.data = [];
expected.purchaseDetails.localizations = [];
mockCMSConfigUtil.transformedPurchaseWithCommonContentForPlanId.mockReturnValueOnce(
expected
);
@ -165,10 +164,10 @@ describe('StripeMapperService', () => {
await stripeMapper.mapCMSToStripePlans([stripePlan], 'en', false);
const actualProduct = mappedPlans[0].product as Stripe.Product;
expect(mappedPlans[0].metadata?.['webIconURL']).toBe(
expected.purchaseDetails.data.attributes.webIcon
expected.purchaseDetails.webIcon
);
expect(actualProduct.metadata?.['webIconURL']).toBe(
expected.purchaseDetails.data.attributes.webIcon
expected.purchaseDetails.webIcon
);
expect(actualProduct.metadata?.['productSet']).toBe(
productMetadata.productSet
@ -196,12 +195,10 @@ describe('StripeMapperService', () => {
await stripeMapper.mapCMSToStripePlans([stripePlan], 'en', false);
const actualProduct = mappedPlans[0].product as Stripe.Product;
expect(mappedPlans[0].metadata?.['webIconURL']).toBe(
expected.purchaseDetails.data.attributes.localizations.data[0]
.attributes.webIcon
expected.purchaseDetails.localizations[0].webIcon
);
expect(actualProduct.metadata?.['webIconURL']).toBe(
expected.purchaseDetails.data.attributes.localizations.data[0]
.attributes.webIcon
expected.purchaseDetails.localizations[0].webIcon
);
expect(actualProduct.metadata?.['productSet']).toBe(
productMetadata.productSet
@ -215,13 +212,9 @@ describe('StripeMapperService', () => {
it('should return data from CMS and not error on locale plan', async () => {
const expected = PurchaseWithDetailsOfferingContentTransformedFactory({
purchaseDetails: {
data: StrapiEntityFactory({
localizations: {
data: [],
},
...PurchaseDetailsTransformedFactory({
details: ['Detail 1 in English'],
}),
localizations: [],
...PurchaseDetailsTransformedFactory({
details: ['Detail 1 in English'],
}),
},
});
@ -260,10 +253,10 @@ describe('StripeMapperService', () => {
const actualProduct1 = mappedPlans[0].product as Stripe.Product;
const actualProduct2 = mappedPlans[1].product as Stripe.Product;
expect(mappedPlans[0].metadata?.['product:details:1']).toBe(
expected.purchaseDetails.data.attributes.details[0]
expected.purchaseDetails.details[0]
);
expect(actualProduct1.metadata?.['product:details:1']).toBe(
expected.purchaseDetails.data.attributes.details[0]
expected.purchaseDetails.details[0]
);
expect(mappedPlans[1].metadata?.['product:details:1']).toBe(
'Detail 1 in French'
@ -276,13 +269,9 @@ describe('StripeMapperService', () => {
it('should return data from Stripe and concat errors for product', async () => {
const expected = PurchaseWithDetailsOfferingContentTransformedFactory({
purchaseDetails: {
data: StrapiEntityFactory({
localizations: {
data: [],
},
...PurchaseDetailsTransformedFactory({
details: ['Detail 1 in English'],
}),
localizations: [],
...PurchaseDetailsTransformedFactory({
details: ['Detail 1 in English'],
}),
},
});

Просмотреть файл

@ -95,18 +95,16 @@ export class StripeMapperService {
continue;
}
const commonContentAttributes =
cmsConfigData.offering.data.attributes.commonContent.data.attributes;
const commonContentAttributes = cmsConfigData.offering.commonContent;
const commonContentAttributesLocalized = commonContentAttributes
.localizations.data.length
? commonContentAttributes.localizations.data[0].attributes
.localizations.length
? commonContentAttributes.localizations[0]
: commonContentAttributes;
const purchaseDetailsAttributes =
cmsConfigData.purchaseDetails.data.attributes;
const purchaseDetailsAttributes = cmsConfigData.purchaseDetails;
const purchaseDetailsLocalizedAttributes = purchaseDetailsAttributes
.localizations.data.length
? purchaseDetailsAttributes.localizations.data[0].attributes
.localizations.length
? purchaseDetailsAttributes.localizations[0]
: purchaseDetailsAttributes;
const planMapper = new PlanMapperUtil(

55
libs/shared/cms/src/__generated__/fragment-masking.ts сгенерированный
Просмотреть файл

@ -1,15 +1,13 @@
/* eslint-disable */
import {
ResultOf,
DocumentTypeDecoration,
TypedDocumentNode,
} from '@graphql-typed-document-node/core';
import { ResultOf, DocumentTypeDecoration, TypedDocumentNode } from '@graphql-typed-document-node/core';
import { FragmentDefinitionNode } from 'graphql';
import { Incremental } from './graphql';
export type FragmentType<
TDocumentType extends DocumentTypeDecoration<any, any>
> = TDocumentType extends DocumentTypeDecoration<infer TType, any>
export type FragmentType<TDocumentType extends DocumentTypeDecoration<any, any>> = TDocumentType extends DocumentTypeDecoration<
infer TType,
any
>
? [TType] extends [{ ' $fragmentName'?: infer TKey }]
? TKey extends string
? { ' $fragmentRefs'?: { [key in TKey]: TType } }
@ -35,10 +33,7 @@ export function useFragment<TType>(
// return nullable if `fragmentType` is nullable or undefined
export function useFragment<TType>(
_documentNode: DocumentTypeDecoration<TType, any>,
fragmentType:
| FragmentType<DocumentTypeDecoration<TType, any>>
| null
| undefined
fragmentType: FragmentType<DocumentTypeDecoration<TType, any>> | null | undefined
): TType | null | undefined;
// return array of non-nullable if `fragmentType` is array of non-nullable
export function useFragment<TType>(
@ -48,10 +43,7 @@ export function useFragment<TType>(
// return array of nullable if `fragmentType` is array of nullable
export function useFragment<TType>(
_documentNode: DocumentTypeDecoration<TType, any>,
fragmentType:
| Array<FragmentType<DocumentTypeDecoration<TType, any>>>
| null
| undefined
fragmentType: Array<FragmentType<DocumentTypeDecoration<TType, any>>> | null | undefined
): Array<TType> | null | undefined;
// return readonly array of non-nullable if `fragmentType` is array of non-nullable
export function useFragment<TType>(
@ -61,23 +53,16 @@ export function useFragment<TType>(
// return readonly array of nullable if `fragmentType` is array of nullable
export function useFragment<TType>(
_documentNode: DocumentTypeDecoration<TType, any>,
fragmentType:
| ReadonlyArray<FragmentType<DocumentTypeDecoration<TType, any>>>
| null
| undefined
fragmentType: ReadonlyArray<FragmentType<DocumentTypeDecoration<TType, any>>> | null | undefined
): ReadonlyArray<TType> | null | undefined;
export function useFragment<TType>(
_documentNode: DocumentTypeDecoration<TType, any>,
fragmentType:
| FragmentType<DocumentTypeDecoration<TType, any>>
| Array<FragmentType<DocumentTypeDecoration<TType, any>>>
| ReadonlyArray<FragmentType<DocumentTypeDecoration<TType, any>>>
| null
| undefined
fragmentType: FragmentType<DocumentTypeDecoration<TType, any>> | Array<FragmentType<DocumentTypeDecoration<TType, any>>> | ReadonlyArray<FragmentType<DocumentTypeDecoration<TType, any>>> | null | undefined
): TType | Array<TType> | ReadonlyArray<TType> | null | undefined {
return fragmentType as any;
}
export function makeFragmentData<
F extends DocumentTypeDecoration<any, any>,
FT extends ResultOf<F>
@ -87,24 +72,16 @@ export function makeFragmentData<
export function isFragmentReady<TQuery, TFrag>(
queryNode: DocumentTypeDecoration<TQuery, any>,
fragmentNode: TypedDocumentNode<TFrag>,
data:
| FragmentType<TypedDocumentNode<Incremental<TFrag>, any>>
| null
| undefined
data: FragmentType<TypedDocumentNode<Incremental<TFrag>, any>> | null | undefined
): data is FragmentType<typeof fragmentNode> {
const deferredFields = (
queryNode as {
__meta__?: { deferredFields: Record<string, (keyof TFrag)[]> };
}
).__meta__?.deferredFields;
const deferredFields = (queryNode as { __meta__?: { deferredFields: Record<string, (keyof TFrag)[]> } }).__meta__
?.deferredFields;
if (!deferredFields) return true;
const fragDef = fragmentNode.definitions[0] as
| FragmentDefinitionNode
| undefined;
const fragDef = fragmentNode.definitions[0] as FragmentDefinitionNode | undefined;
const fragName = fragDef?.name?.value;
const fields = (fragName && deferredFields[fragName]) || [];
return fields.length > 0 && fields.every((field) => data && field in data);
return fields.length > 0 && fields.every(field => data && field in data);
}

59
libs/shared/cms/src/__generated__/gql.ts сгенерированный
Просмотреть файл

@ -13,22 +13,14 @@ import { TypedDocumentNode as DocumentNode } from '@graphql-typed-document-node/
* Therefore it is highly recommended to use the babel or swc plugin for production.
*/
const documents = {
'\n query CapabilityServiceByPlanIds(\n $skip: Int!\n $limit: Int!\n $stripePlanIds: [String]!\n ) {\n purchases(\n filters: {\n or: [\n { stripePlanChoices: { stripePlanChoice: { in: $stripePlanIds } } }\n {\n offering: {\n stripeLegacyPlans: { stripeLegacyPlan: { in: $stripePlanIds } }\n }\n }\n ]\n }\n pagination: { start: $skip, limit: $limit }\n ) {\n meta {\n pagination {\n total\n }\n }\n data {\n attributes {\n stripePlanChoices {\n stripePlanChoice\n }\n offering {\n data {\n attributes {\n stripeLegacyPlans(pagination: { limit: 200 }) {\n stripeLegacyPlan\n }\n capabilities {\n data {\n attributes {\n slug\n services {\n data {\n attributes {\n oauthClientId\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n':
types.CapabilityServiceByPlanIdsDocument,
'\n query EligibilityContentByOffering($apiIdentifier: String!) {\n offerings(\n pagination: { start: 0, limit: 2 }\n filters: { apiIdentifier: { eq: $apiIdentifier } }\n ) {\n data {\n attributes {\n apiIdentifier\n stripeProductId\n defaultPurchase {\n data {\n attributes {\n stripePlanChoices {\n stripePlanChoice\n }\n }\n }\n }\n subGroups {\n data {\n attributes {\n groupName\n offerings {\n data {\n attributes {\n apiIdentifier\n stripeProductId\n defaultPurchase {\n data {\n attributes {\n stripePlanChoices {\n stripePlanChoice\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n':
types.EligibilityContentByOfferingDocument,
'\n query EligibilityContentByPlanIds(\n $skip: Int!\n $limit: Int!\n $stripePlanIds: [String]!\n ) {\n purchases(\n pagination: { start: $skip, limit: $limit }\n filters: {\n or: [\n { stripePlanChoices: { stripePlanChoice: { in: $stripePlanIds } } }\n {\n offering: {\n stripeLegacyPlans: { stripeLegacyPlan: { in: $stripePlanIds } }\n }\n }\n ]\n }\n ) {\n meta {\n pagination {\n total\n }\n }\n data {\n attributes {\n stripePlanChoices {\n stripePlanChoice\n }\n offering {\n data {\n attributes {\n stripeProductId\n stripeLegacyPlans(pagination: { limit: 200 }) {\n stripeLegacyPlan\n }\n countries\n subGroups {\n data {\n attributes {\n groupName\n offerings {\n data {\n attributes {\n stripeProductId\n stripeLegacyPlans(pagination: { limit: 200 }) {\n stripeLegacyPlan\n }\n countries\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n':
types.EligibilityContentByPlanIdsDocument,
'\n query Locales {\n i18NLocales {\n data {\n attributes {\n code\n }\n }\n }\n }\n':
types.LocalesDocument,
'\n query Offering($id: ID!, $locale: String!) {\n offering(id: $id) {\n data {\n attributes {\n stripeProductId\n countries\n defaultPurchase {\n data {\n attributes {\n purchaseDetails {\n data {\n attributes {\n productName\n details\n subtitle\n webIcon\n localizations(filters: { locale: { eq: $locale } }) {\n data {\n attributes {\n productName\n details\n subtitle\n webIcon\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n':
types.OfferingDocument,
'\n query PageContentForOffering($locale: String!, $apiIdentifier: String!) {\n offerings(\n pagination: { start: 0, limit: 2 }\n filters: { apiIdentifier: { eq: $apiIdentifier } }\n ) {\n meta {\n pagination {\n total\n }\n }\n data {\n attributes {\n apiIdentifier\n stripeProductId\n defaultPurchase {\n data {\n attributes {\n purchaseDetails {\n data {\n attributes {\n details\n productName\n subtitle\n webIcon\n localizations(filters: { locale: { eq: $locale } }) {\n data {\n attributes {\n details\n productName\n subtitle\n webIcon\n }\n }\n }\n }\n }\n }\n }\n }\n }\n commonContent {\n data {\n attributes {\n privacyNoticeUrl\n privacyNoticeDownloadUrl\n termsOfServiceUrl\n termsOfServiceDownloadUrl\n cancellationUrl\n emailIcon\n successActionButtonUrl\n successActionButtonLabel\n newsletterLabelTextCode\n newsletterSlug\n localizations(filters: { locale: { eq: $locale } }) {\n data {\n attributes {\n privacyNoticeUrl\n privacyNoticeDownloadUrl\n termsOfServiceUrl\n termsOfServiceDownloadUrl\n cancellationUrl\n emailIcon\n successActionButtonUrl\n successActionButtonLabel\n newsletterLabelTextCode\n newsletterSlug\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n':
types.PageContentForOfferingDocument,
'\n query PurchaseWithDetailsOfferingContent(\n $skip: Int!\n $limit: Int!\n $locale: String!\n $stripePlanIds: [String]!\n ) {\n purchases(\n pagination: { start: $skip, limit: $limit }\n filters: {\n or: [\n { stripePlanChoices: { stripePlanChoice: { in: $stripePlanIds } } }\n {\n offering: {\n stripeLegacyPlans: { stripeLegacyPlan: { in: $stripePlanIds } }\n }\n }\n ]\n }\n ) {\n data {\n attributes {\n stripePlanChoices {\n stripePlanChoice\n }\n purchaseDetails {\n data {\n attributes {\n details\n productName\n subtitle\n webIcon\n localizations(filters: { locale: { eq: $locale } }) {\n data {\n attributes {\n details\n productName\n subtitle\n webIcon\n }\n }\n }\n }\n }\n }\n offering {\n data {\n attributes {\n stripeProductId\n stripeLegacyPlans(pagination: { limit: 200 }) {\n stripeLegacyPlan\n }\n commonContent {\n data {\n attributes {\n privacyNoticeUrl\n privacyNoticeDownloadUrl\n termsOfServiceUrl\n termsOfServiceDownloadUrl\n cancellationUrl\n emailIcon\n successActionButtonUrl\n successActionButtonLabel\n newsletterLabelTextCode\n newsletterSlug\n localizations(filters: { locale: { eq: $locale } }) {\n data {\n attributes {\n privacyNoticeUrl\n privacyNoticeDownloadUrl\n termsOfServiceUrl\n termsOfServiceDownloadUrl\n cancellationUrl\n emailIcon\n successActionButtonUrl\n successActionButtonLabel\n newsletterLabelTextCode\n newsletterSlug\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n':
types.PurchaseWithDetailsOfferingContentDocument,
'\n query ServicesWithCapabilities($skip: Int!, $limit: Int!) {\n services(pagination: { start: $skip, limit: $limit }) {\n data {\n attributes {\n oauthClientId\n capabilities {\n data {\n attributes {\n slug\n }\n }\n }\n }\n }\n }\n }\n':
types.ServicesWithCapabilitiesDocument,
"\n query CapabilityServiceByPlanIds($stripePlanIds: [String]!) {\n purchases(\n filters: {\n or: [\n { stripePlanChoices: { stripePlanChoice: { in: $stripePlanIds } } }\n {\n offering: {\n stripeLegacyPlans: { stripeLegacyPlan: { in: $stripePlanIds } }\n }\n }\n ]\n }\n pagination: { limit: 200 }\n ) {\n stripePlanChoices {\n stripePlanChoice\n }\n offering {\n stripeLegacyPlans(pagination: { limit: 200 }) {\n stripeLegacyPlan\n }\n capabilities {\n slug\n services {\n oauthClientId\n }\n }\n }\n }\n }\n": types.CapabilityServiceByPlanIdsDocument,
"\n query EligibilityContentByOffering($apiIdentifier: String!) {\n offerings(\n filters: { apiIdentifier: { eq: $apiIdentifier } }\n pagination: { limit: 200 }\n ) {\n apiIdentifier\n stripeProductId\n defaultPurchase {\n stripePlanChoices {\n stripePlanChoice\n }\n }\n subGroups {\n groupName\n offerings {\n apiIdentifier\n stripeProductId\n defaultPurchase {\n stripePlanChoices {\n stripePlanChoice\n }\n }\n }\n }\n }\n }\n": types.EligibilityContentByOfferingDocument,
"\n query EligibilityContentByPlanIds($stripePlanIds: [String]!) {\n purchases(\n filters: {\n or: [\n { stripePlanChoices: { stripePlanChoice: { in: $stripePlanIds } } }\n {\n offering: {\n stripeLegacyPlans: { stripeLegacyPlan: { in: $stripePlanIds } }\n }\n }\n ]\n }\n pagination: { limit: 200 }\n ) {\n stripePlanChoices {\n stripePlanChoice\n }\n offering {\n stripeProductId\n stripeLegacyPlans(pagination: { limit: 200 }) {\n stripeLegacyPlan\n }\n countries\n subGroups {\n groupName\n offerings {\n stripeProductId\n stripeLegacyPlans(pagination: { limit: 200 }) {\n stripeLegacyPlan\n }\n countries\n }\n }\n }\n }\n }\n": types.EligibilityContentByPlanIdsDocument,
"\n query Locales {\n i18NLocales {\n code\n }\n }\n": types.LocalesDocument,
"\n query Offering($id: ID!, $locale: String!) {\n offering(documentId: $id) {\n stripeProductId\n countries\n defaultPurchase {\n purchaseDetails {\n productName\n details\n subtitle\n webIcon\n localizations(filters: { locale: { eq: $locale } }) {\n productName\n details\n subtitle\n webIcon\n }\n }\n }\n }\n }\n": types.OfferingDocument,
"\n query PageContentForOffering($locale: String!, $apiIdentifier: String!) {\n offerings(\n filters: { apiIdentifier: { eq: $apiIdentifier } }\n pagination: { limit: 200 }\n ) {\n apiIdentifier\n stripeProductId\n defaultPurchase {\n purchaseDetails {\n details\n productName\n subtitle\n webIcon\n localizations(filters: { locale: { eq: $locale } }) {\n details\n productName\n subtitle\n webIcon\n }\n }\n }\n commonContent {\n privacyNoticeUrl\n privacyNoticeDownloadUrl\n termsOfServiceUrl\n termsOfServiceDownloadUrl\n cancellationUrl\n emailIcon\n successActionButtonUrl\n successActionButtonLabel\n newsletterLabelTextCode\n newsletterSlug\n localizations(filters: { locale: { eq: $locale } }) {\n privacyNoticeUrl\n privacyNoticeDownloadUrl\n termsOfServiceUrl\n termsOfServiceDownloadUrl\n cancellationUrl\n emailIcon\n successActionButtonUrl\n successActionButtonLabel\n newsletterLabelTextCode\n newsletterSlug\n }\n }\n }\n }\n": types.PageContentForOfferingDocument,
"\n query PurchaseWithDetailsOfferingContent(\n $locale: String!\n $stripePlanIds: [String]!\n ) {\n purchases(\n filters: {\n or: [\n { stripePlanChoices: { stripePlanChoice: { in: $stripePlanIds } } }\n {\n offering: {\n stripeLegacyPlans: { stripeLegacyPlan: { in: $stripePlanIds } }\n }\n }\n ]\n }\n pagination: { limit: 500 }\n ) {\n stripePlanChoices {\n stripePlanChoice\n }\n purchaseDetails {\n details\n productName\n subtitle\n webIcon\n localizations(filters: { locale: { eq: $locale } }) {\n details\n productName\n subtitle\n webIcon\n }\n }\n offering {\n stripeProductId\n stripeLegacyPlans(pagination: { limit: 200 }) {\n stripeLegacyPlan\n }\n commonContent {\n privacyNoticeUrl\n privacyNoticeDownloadUrl\n termsOfServiceUrl\n termsOfServiceDownloadUrl\n cancellationUrl\n emailIcon\n successActionButtonUrl\n successActionButtonLabel\n newsletterLabelTextCode\n newsletterSlug\n localizations(filters: { locale: { eq: $locale } }) {\n privacyNoticeUrl\n privacyNoticeDownloadUrl\n termsOfServiceUrl\n termsOfServiceDownloadUrl\n cancellationUrl\n emailIcon\n successActionButtonUrl\n successActionButtonLabel\n newsletterLabelTextCode\n newsletterSlug\n }\n }\n }\n }\n }\n": types.PurchaseWithDetailsOfferingContentDocument,
"\n query ServicesWithCapabilities {\n services(pagination: { limit: 500 }) {\n oauthClientId\n capabilities {\n slug\n }\n }\n }\n": types.ServicesWithCapabilitiesDocument,
};
/**
@ -48,55 +40,38 @@ export function graphql(source: string): unknown;
/**
* The graphql function is used to parse GraphQL queries into a document that can be used by GraphQL clients.
*/
export function graphql(
source: '\n query CapabilityServiceByPlanIds(\n $skip: Int!\n $limit: Int!\n $stripePlanIds: [String]!\n ) {\n purchases(\n filters: {\n or: [\n { stripePlanChoices: { stripePlanChoice: { in: $stripePlanIds } } }\n {\n offering: {\n stripeLegacyPlans: { stripeLegacyPlan: { in: $stripePlanIds } }\n }\n }\n ]\n }\n pagination: { start: $skip, limit: $limit }\n ) {\n meta {\n pagination {\n total\n }\n }\n data {\n attributes {\n stripePlanChoices {\n stripePlanChoice\n }\n offering {\n data {\n attributes {\n stripeLegacyPlans(pagination: { limit: 200 }) {\n stripeLegacyPlan\n }\n capabilities {\n data {\n attributes {\n slug\n services {\n data {\n attributes {\n oauthClientId\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n'
): (typeof documents)['\n query CapabilityServiceByPlanIds(\n $skip: Int!\n $limit: Int!\n $stripePlanIds: [String]!\n ) {\n purchases(\n filters: {\n or: [\n { stripePlanChoices: { stripePlanChoice: { in: $stripePlanIds } } }\n {\n offering: {\n stripeLegacyPlans: { stripeLegacyPlan: { in: $stripePlanIds } }\n }\n }\n ]\n }\n pagination: { start: $skip, limit: $limit }\n ) {\n meta {\n pagination {\n total\n }\n }\n data {\n attributes {\n stripePlanChoices {\n stripePlanChoice\n }\n offering {\n data {\n attributes {\n stripeLegacyPlans(pagination: { limit: 200 }) {\n stripeLegacyPlan\n }\n capabilities {\n data {\n attributes {\n slug\n services {\n data {\n attributes {\n oauthClientId\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n'];
export function graphql(source: "\n query CapabilityServiceByPlanIds($stripePlanIds: [String]!) {\n purchases(\n filters: {\n or: [\n { stripePlanChoices: { stripePlanChoice: { in: $stripePlanIds } } }\n {\n offering: {\n stripeLegacyPlans: { stripeLegacyPlan: { in: $stripePlanIds } }\n }\n }\n ]\n }\n pagination: { limit: 200 }\n ) {\n stripePlanChoices {\n stripePlanChoice\n }\n offering {\n stripeLegacyPlans(pagination: { limit: 200 }) {\n stripeLegacyPlan\n }\n capabilities {\n slug\n services {\n oauthClientId\n }\n }\n }\n }\n }\n"): (typeof documents)["\n query CapabilityServiceByPlanIds($stripePlanIds: [String]!) {\n purchases(\n filters: {\n or: [\n { stripePlanChoices: { stripePlanChoice: { in: $stripePlanIds } } }\n {\n offering: {\n stripeLegacyPlans: { stripeLegacyPlan: { in: $stripePlanIds } }\n }\n }\n ]\n }\n pagination: { limit: 200 }\n ) {\n stripePlanChoices {\n stripePlanChoice\n }\n offering {\n stripeLegacyPlans(pagination: { limit: 200 }) {\n stripeLegacyPlan\n }\n capabilities {\n slug\n services {\n oauthClientId\n }\n }\n }\n }\n }\n"];
/**
* The graphql function is used to parse GraphQL queries into a document that can be used by GraphQL clients.
*/
export function graphql(
source: '\n query EligibilityContentByOffering($apiIdentifier: String!) {\n offerings(\n pagination: { start: 0, limit: 2 }\n filters: { apiIdentifier: { eq: $apiIdentifier } }\n ) {\n data {\n attributes {\n apiIdentifier\n stripeProductId\n defaultPurchase {\n data {\n attributes {\n stripePlanChoices {\n stripePlanChoice\n }\n }\n }\n }\n subGroups {\n data {\n attributes {\n groupName\n offerings {\n data {\n attributes {\n apiIdentifier\n stripeProductId\n defaultPurchase {\n data {\n attributes {\n stripePlanChoices {\n stripePlanChoice\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n'
): (typeof documents)['\n query EligibilityContentByOffering($apiIdentifier: String!) {\n offerings(\n pagination: { start: 0, limit: 2 }\n filters: { apiIdentifier: { eq: $apiIdentifier } }\n ) {\n data {\n attributes {\n apiIdentifier\n stripeProductId\n defaultPurchase {\n data {\n attributes {\n stripePlanChoices {\n stripePlanChoice\n }\n }\n }\n }\n subGroups {\n data {\n attributes {\n groupName\n offerings {\n data {\n attributes {\n apiIdentifier\n stripeProductId\n defaultPurchase {\n data {\n attributes {\n stripePlanChoices {\n stripePlanChoice\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n'];
export function graphql(source: "\n query EligibilityContentByOffering($apiIdentifier: String!) {\n offerings(\n filters: { apiIdentifier: { eq: $apiIdentifier } }\n pagination: { limit: 200 }\n ) {\n apiIdentifier\n stripeProductId\n defaultPurchase {\n stripePlanChoices {\n stripePlanChoice\n }\n }\n subGroups {\n groupName\n offerings {\n apiIdentifier\n stripeProductId\n defaultPurchase {\n stripePlanChoices {\n stripePlanChoice\n }\n }\n }\n }\n }\n }\n"): (typeof documents)["\n query EligibilityContentByOffering($apiIdentifier: String!) {\n offerings(\n filters: { apiIdentifier: { eq: $apiIdentifier } }\n pagination: { limit: 200 }\n ) {\n apiIdentifier\n stripeProductId\n defaultPurchase {\n stripePlanChoices {\n stripePlanChoice\n }\n }\n subGroups {\n groupName\n offerings {\n apiIdentifier\n stripeProductId\n defaultPurchase {\n stripePlanChoices {\n stripePlanChoice\n }\n }\n }\n }\n }\n }\n"];
/**
* The graphql function is used to parse GraphQL queries into a document that can be used by GraphQL clients.
*/
export function graphql(
source: '\n query EligibilityContentByPlanIds(\n $skip: Int!\n $limit: Int!\n $stripePlanIds: [String]!\n ) {\n purchases(\n pagination: { start: $skip, limit: $limit }\n filters: {\n or: [\n { stripePlanChoices: { stripePlanChoice: { in: $stripePlanIds } } }\n {\n offering: {\n stripeLegacyPlans: { stripeLegacyPlan: { in: $stripePlanIds } }\n }\n }\n ]\n }\n ) {\n meta {\n pagination {\n total\n }\n }\n data {\n attributes {\n stripePlanChoices {\n stripePlanChoice\n }\n offering {\n data {\n attributes {\n stripeProductId\n stripeLegacyPlans(pagination: { limit: 200 }) {\n stripeLegacyPlan\n }\n countries\n subGroups {\n data {\n attributes {\n groupName\n offerings {\n data {\n attributes {\n stripeProductId\n stripeLegacyPlans(pagination: { limit: 200 }) {\n stripeLegacyPlan\n }\n countries\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n'
): (typeof documents)['\n query EligibilityContentByPlanIds(\n $skip: Int!\n $limit: Int!\n $stripePlanIds: [String]!\n ) {\n purchases(\n pagination: { start: $skip, limit: $limit }\n filters: {\n or: [\n { stripePlanChoices: { stripePlanChoice: { in: $stripePlanIds } } }\n {\n offering: {\n stripeLegacyPlans: { stripeLegacyPlan: { in: $stripePlanIds } }\n }\n }\n ]\n }\n ) {\n meta {\n pagination {\n total\n }\n }\n data {\n attributes {\n stripePlanChoices {\n stripePlanChoice\n }\n offering {\n data {\n attributes {\n stripeProductId\n stripeLegacyPlans(pagination: { limit: 200 }) {\n stripeLegacyPlan\n }\n countries\n subGroups {\n data {\n attributes {\n groupName\n offerings {\n data {\n attributes {\n stripeProductId\n stripeLegacyPlans(pagination: { limit: 200 }) {\n stripeLegacyPlan\n }\n countries\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n'];
export function graphql(source: "\n query EligibilityContentByPlanIds($stripePlanIds: [String]!) {\n purchases(\n filters: {\n or: [\n { stripePlanChoices: { stripePlanChoice: { in: $stripePlanIds } } }\n {\n offering: {\n stripeLegacyPlans: { stripeLegacyPlan: { in: $stripePlanIds } }\n }\n }\n ]\n }\n pagination: { limit: 200 }\n ) {\n stripePlanChoices {\n stripePlanChoice\n }\n offering {\n stripeProductId\n stripeLegacyPlans(pagination: { limit: 200 }) {\n stripeLegacyPlan\n }\n countries\n subGroups {\n groupName\n offerings {\n stripeProductId\n stripeLegacyPlans(pagination: { limit: 200 }) {\n stripeLegacyPlan\n }\n countries\n }\n }\n }\n }\n }\n"): (typeof documents)["\n query EligibilityContentByPlanIds($stripePlanIds: [String]!) {\n purchases(\n filters: {\n or: [\n { stripePlanChoices: { stripePlanChoice: { in: $stripePlanIds } } }\n {\n offering: {\n stripeLegacyPlans: { stripeLegacyPlan: { in: $stripePlanIds } }\n }\n }\n ]\n }\n pagination: { limit: 200 }\n ) {\n stripePlanChoices {\n stripePlanChoice\n }\n offering {\n stripeProductId\n stripeLegacyPlans(pagination: { limit: 200 }) {\n stripeLegacyPlan\n }\n countries\n subGroups {\n groupName\n offerings {\n stripeProductId\n stripeLegacyPlans(pagination: { limit: 200 }) {\n stripeLegacyPlan\n }\n countries\n }\n }\n }\n }\n }\n"];
/**
* The graphql function is used to parse GraphQL queries into a document that can be used by GraphQL clients.
*/
export function graphql(
source: '\n query Locales {\n i18NLocales {\n data {\n attributes {\n code\n }\n }\n }\n }\n'
): (typeof documents)['\n query Locales {\n i18NLocales {\n data {\n attributes {\n code\n }\n }\n }\n }\n'];
export function graphql(source: "\n query Locales {\n i18NLocales {\n code\n }\n }\n"): (typeof documents)["\n query Locales {\n i18NLocales {\n code\n }\n }\n"];
/**
* The graphql function is used to parse GraphQL queries into a document that can be used by GraphQL clients.
*/
export function graphql(
source: '\n query Offering($id: ID!, $locale: String!) {\n offering(id: $id) {\n data {\n attributes {\n stripeProductId\n countries\n defaultPurchase {\n data {\n attributes {\n purchaseDetails {\n data {\n attributes {\n productName\n details\n subtitle\n webIcon\n localizations(filters: { locale: { eq: $locale } }) {\n data {\n attributes {\n productName\n details\n subtitle\n webIcon\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n'
): (typeof documents)['\n query Offering($id: ID!, $locale: String!) {\n offering(id: $id) {\n data {\n attributes {\n stripeProductId\n countries\n defaultPurchase {\n data {\n attributes {\n purchaseDetails {\n data {\n attributes {\n productName\n details\n subtitle\n webIcon\n localizations(filters: { locale: { eq: $locale } }) {\n data {\n attributes {\n productName\n details\n subtitle\n webIcon\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n'];
export function graphql(source: "\n query Offering($id: ID!, $locale: String!) {\n offering(documentId: $id) {\n stripeProductId\n countries\n defaultPurchase {\n purchaseDetails {\n productName\n details\n subtitle\n webIcon\n localizations(filters: { locale: { eq: $locale } }) {\n productName\n details\n subtitle\n webIcon\n }\n }\n }\n }\n }\n"): (typeof documents)["\n query Offering($id: ID!, $locale: String!) {\n offering(documentId: $id) {\n stripeProductId\n countries\n defaultPurchase {\n purchaseDetails {\n productName\n details\n subtitle\n webIcon\n localizations(filters: { locale: { eq: $locale } }) {\n productName\n details\n subtitle\n webIcon\n }\n }\n }\n }\n }\n"];
/**
* The graphql function is used to parse GraphQL queries into a document that can be used by GraphQL clients.
*/
export function graphql(
source: '\n query PageContentForOffering($locale: String!, $apiIdentifier: String!) {\n offerings(\n pagination: { start: 0, limit: 2 }\n filters: { apiIdentifier: { eq: $apiIdentifier } }\n ) {\n meta {\n pagination {\n total\n }\n }\n data {\n attributes {\n apiIdentifier\n stripeProductId\n defaultPurchase {\n data {\n attributes {\n purchaseDetails {\n data {\n attributes {\n details\n productName\n subtitle\n webIcon\n localizations(filters: { locale: { eq: $locale } }) {\n data {\n attributes {\n details\n productName\n subtitle\n webIcon\n }\n }\n }\n }\n }\n }\n }\n }\n }\n commonContent {\n data {\n attributes {\n privacyNoticeUrl\n privacyNoticeDownloadUrl\n termsOfServiceUrl\n termsOfServiceDownloadUrl\n cancellationUrl\n emailIcon\n successActionButtonUrl\n successActionButtonLabel\n newsletterLabelTextCode\n newsletterSlug\n localizations(filters: { locale: { eq: $locale } }) {\n data {\n attributes {\n privacyNoticeUrl\n privacyNoticeDownloadUrl\n termsOfServiceUrl\n termsOfServiceDownloadUrl\n cancellationUrl\n emailIcon\n successActionButtonUrl\n successActionButtonLabel\n newsletterLabelTextCode\n newsletterSlug\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n'
): (typeof documents)['\n query PageContentForOffering($locale: String!, $apiIdentifier: String!) {\n offerings(\n pagination: { start: 0, limit: 2 }\n filters: { apiIdentifier: { eq: $apiIdentifier } }\n ) {\n meta {\n pagination {\n total\n }\n }\n data {\n attributes {\n apiIdentifier\n stripeProductId\n defaultPurchase {\n data {\n attributes {\n purchaseDetails {\n data {\n attributes {\n details\n productName\n subtitle\n webIcon\n localizations(filters: { locale: { eq: $locale } }) {\n data {\n attributes {\n details\n productName\n subtitle\n webIcon\n }\n }\n }\n }\n }\n }\n }\n }\n }\n commonContent {\n data {\n attributes {\n privacyNoticeUrl\n privacyNoticeDownloadUrl\n termsOfServiceUrl\n termsOfServiceDownloadUrl\n cancellationUrl\n emailIcon\n successActionButtonUrl\n successActionButtonLabel\n newsletterLabelTextCode\n newsletterSlug\n localizations(filters: { locale: { eq: $locale } }) {\n data {\n attributes {\n privacyNoticeUrl\n privacyNoticeDownloadUrl\n termsOfServiceUrl\n termsOfServiceDownloadUrl\n cancellationUrl\n emailIcon\n successActionButtonUrl\n successActionButtonLabel\n newsletterLabelTextCode\n newsletterSlug\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n'];
export function graphql(source: "\n query PageContentForOffering($locale: String!, $apiIdentifier: String!) {\n offerings(\n filters: { apiIdentifier: { eq: $apiIdentifier } }\n pagination: { limit: 200 }\n ) {\n apiIdentifier\n stripeProductId\n defaultPurchase {\n purchaseDetails {\n details\n productName\n subtitle\n webIcon\n localizations(filters: { locale: { eq: $locale } }) {\n details\n productName\n subtitle\n webIcon\n }\n }\n }\n commonContent {\n privacyNoticeUrl\n privacyNoticeDownloadUrl\n termsOfServiceUrl\n termsOfServiceDownloadUrl\n cancellationUrl\n emailIcon\n successActionButtonUrl\n successActionButtonLabel\n newsletterLabelTextCode\n newsletterSlug\n localizations(filters: { locale: { eq: $locale } }) {\n privacyNoticeUrl\n privacyNoticeDownloadUrl\n termsOfServiceUrl\n termsOfServiceDownloadUrl\n cancellationUrl\n emailIcon\n successActionButtonUrl\n successActionButtonLabel\n newsletterLabelTextCode\n newsletterSlug\n }\n }\n }\n }\n"): (typeof documents)["\n query PageContentForOffering($locale: String!, $apiIdentifier: String!) {\n offerings(\n filters: { apiIdentifier: { eq: $apiIdentifier } }\n pagination: { limit: 200 }\n ) {\n apiIdentifier\n stripeProductId\n defaultPurchase {\n purchaseDetails {\n details\n productName\n subtitle\n webIcon\n localizations(filters: { locale: { eq: $locale } }) {\n details\n productName\n subtitle\n webIcon\n }\n }\n }\n commonContent {\n privacyNoticeUrl\n privacyNoticeDownloadUrl\n termsOfServiceUrl\n termsOfServiceDownloadUrl\n cancellationUrl\n emailIcon\n successActionButtonUrl\n successActionButtonLabel\n newsletterLabelTextCode\n newsletterSlug\n localizations(filters: { locale: { eq: $locale } }) {\n privacyNoticeUrl\n privacyNoticeDownloadUrl\n termsOfServiceUrl\n termsOfServiceDownloadUrl\n cancellationUrl\n emailIcon\n successActionButtonUrl\n successActionButtonLabel\n newsletterLabelTextCode\n newsletterSlug\n }\n }\n }\n }\n"];
/**
* The graphql function is used to parse GraphQL queries into a document that can be used by GraphQL clients.
*/
export function graphql(
source: '\n query PurchaseWithDetailsOfferingContent(\n $skip: Int!\n $limit: Int!\n $locale: String!\n $stripePlanIds: [String]!\n ) {\n purchases(\n pagination: { start: $skip, limit: $limit }\n filters: {\n or: [\n { stripePlanChoices: { stripePlanChoice: { in: $stripePlanIds } } }\n {\n offering: {\n stripeLegacyPlans: { stripeLegacyPlan: { in: $stripePlanIds } }\n }\n }\n ]\n }\n ) {\n data {\n attributes {\n stripePlanChoices {\n stripePlanChoice\n }\n purchaseDetails {\n data {\n attributes {\n details\n productName\n subtitle\n webIcon\n localizations(filters: { locale: { eq: $locale } }) {\n data {\n attributes {\n details\n productName\n subtitle\n webIcon\n }\n }\n }\n }\n }\n }\n offering {\n data {\n attributes {\n stripeProductId\n stripeLegacyPlans(pagination: { limit: 200 }) {\n stripeLegacyPlan\n }\n commonContent {\n data {\n attributes {\n privacyNoticeUrl\n privacyNoticeDownloadUrl\n termsOfServiceUrl\n termsOfServiceDownloadUrl\n cancellationUrl\n emailIcon\n successActionButtonUrl\n successActionButtonLabel\n newsletterLabelTextCode\n newsletterSlug\n localizations(filters: { locale: { eq: $locale } }) {\n data {\n attributes {\n privacyNoticeUrl\n privacyNoticeDownloadUrl\n termsOfServiceUrl\n termsOfServiceDownloadUrl\n cancellationUrl\n emailIcon\n successActionButtonUrl\n successActionButtonLabel\n newsletterLabelTextCode\n newsletterSlug\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n'
): (typeof documents)['\n query PurchaseWithDetailsOfferingContent(\n $skip: Int!\n $limit: Int!\n $locale: String!\n $stripePlanIds: [String]!\n ) {\n purchases(\n pagination: { start: $skip, limit: $limit }\n filters: {\n or: [\n { stripePlanChoices: { stripePlanChoice: { in: $stripePlanIds } } }\n {\n offering: {\n stripeLegacyPlans: { stripeLegacyPlan: { in: $stripePlanIds } }\n }\n }\n ]\n }\n ) {\n data {\n attributes {\n stripePlanChoices {\n stripePlanChoice\n }\n purchaseDetails {\n data {\n attributes {\n details\n productName\n subtitle\n webIcon\n localizations(filters: { locale: { eq: $locale } }) {\n data {\n attributes {\n details\n productName\n subtitle\n webIcon\n }\n }\n }\n }\n }\n }\n offering {\n data {\n attributes {\n stripeProductId\n stripeLegacyPlans(pagination: { limit: 200 }) {\n stripeLegacyPlan\n }\n commonContent {\n data {\n attributes {\n privacyNoticeUrl\n privacyNoticeDownloadUrl\n termsOfServiceUrl\n termsOfServiceDownloadUrl\n cancellationUrl\n emailIcon\n successActionButtonUrl\n successActionButtonLabel\n newsletterLabelTextCode\n newsletterSlug\n localizations(filters: { locale: { eq: $locale } }) {\n data {\n attributes {\n privacyNoticeUrl\n privacyNoticeDownloadUrl\n termsOfServiceUrl\n termsOfServiceDownloadUrl\n cancellationUrl\n emailIcon\n successActionButtonUrl\n successActionButtonLabel\n newsletterLabelTextCode\n newsletterSlug\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n }\n'];
export function graphql(source: "\n query PurchaseWithDetailsOfferingContent(\n $locale: String!\n $stripePlanIds: [String]!\n ) {\n purchases(\n filters: {\n or: [\n { stripePlanChoices: { stripePlanChoice: { in: $stripePlanIds } } }\n {\n offering: {\n stripeLegacyPlans: { stripeLegacyPlan: { in: $stripePlanIds } }\n }\n }\n ]\n }\n pagination: { limit: 500 }\n ) {\n stripePlanChoices {\n stripePlanChoice\n }\n purchaseDetails {\n details\n productName\n subtitle\n webIcon\n localizations(filters: { locale: { eq: $locale } }) {\n details\n productName\n subtitle\n webIcon\n }\n }\n offering {\n stripeProductId\n stripeLegacyPlans(pagination: { limit: 200 }) {\n stripeLegacyPlan\n }\n commonContent {\n privacyNoticeUrl\n privacyNoticeDownloadUrl\n termsOfServiceUrl\n termsOfServiceDownloadUrl\n cancellationUrl\n emailIcon\n successActionButtonUrl\n successActionButtonLabel\n newsletterLabelTextCode\n newsletterSlug\n localizations(filters: { locale: { eq: $locale } }) {\n privacyNoticeUrl\n privacyNoticeDownloadUrl\n termsOfServiceUrl\n termsOfServiceDownloadUrl\n cancellationUrl\n emailIcon\n successActionButtonUrl\n successActionButtonLabel\n newsletterLabelTextCode\n newsletterSlug\n }\n }\n }\n }\n }\n"): (typeof documents)["\n query PurchaseWithDetailsOfferingContent(\n $locale: String!\n $stripePlanIds: [String]!\n ) {\n purchases(\n filters: {\n or: [\n { stripePlanChoices: { stripePlanChoice: { in: $stripePlanIds } } }\n {\n offering: {\n stripeLegacyPlans: { stripeLegacyPlan: { in: $stripePlanIds } }\n }\n }\n ]\n }\n pagination: { limit: 500 }\n ) {\n stripePlanChoices {\n stripePlanChoice\n }\n purchaseDetails {\n details\n productName\n subtitle\n webIcon\n localizations(filters: { locale: { eq: $locale } }) {\n details\n productName\n subtitle\n webIcon\n }\n }\n offering {\n stripeProductId\n stripeLegacyPlans(pagination: { limit: 200 }) {\n stripeLegacyPlan\n }\n commonContent {\n privacyNoticeUrl\n privacyNoticeDownloadUrl\n termsOfServiceUrl\n termsOfServiceDownloadUrl\n cancellationUrl\n emailIcon\n successActionButtonUrl\n successActionButtonLabel\n newsletterLabelTextCode\n newsletterSlug\n localizations(filters: { locale: { eq: $locale } }) {\n privacyNoticeUrl\n privacyNoticeDownloadUrl\n termsOfServiceUrl\n termsOfServiceDownloadUrl\n cancellationUrl\n emailIcon\n successActionButtonUrl\n successActionButtonLabel\n newsletterLabelTextCode\n newsletterSlug\n }\n }\n }\n }\n }\n"];
/**
* The graphql function is used to parse GraphQL queries into a document that can be used by GraphQL clients.
*/
export function graphql(
source: '\n query ServicesWithCapabilities($skip: Int!, $limit: Int!) {\n services(pagination: { start: $skip, limit: $limit }) {\n data {\n attributes {\n oauthClientId\n capabilities {\n data {\n attributes {\n slug\n }\n }\n }\n }\n }\n }\n }\n'
): (typeof documents)['\n query ServicesWithCapabilities($skip: Int!, $limit: Int!) {\n services(pagination: { start: $skip, limit: $limit }) {\n data {\n attributes {\n oauthClientId\n capabilities {\n data {\n attributes {\n slug\n }\n }\n }\n }\n }\n }\n }\n'];
export function graphql(source: "\n query ServicesWithCapabilities {\n services(pagination: { limit: 500 }) {\n oauthClientId\n capabilities {\n slug\n }\n }\n }\n"): (typeof documents)["\n query ServicesWithCapabilities {\n services(pagination: { limit: 500 }) {\n oauthClientId\n capabilities {\n slug\n }\n }\n }\n"];
export function graphql(source: string) {
return (documents as any)[source] ?? {};
}
export type DocumentType<TDocumentNode extends DocumentNode<any, any>> =
TDocumentNode extends DocumentNode<infer TType, any> ? TType : never;
export type DocumentType<TDocumentNode extends DocumentNode<any, any>> = TDocumentNode extends DocumentNode< infer TType, any> ? TType : never;

5396
libs/shared/cms/src/__generated__/graphql.ts сгенерированный

Различия файлов скрыты, потому что одна или несколько строк слишком длинны

4
libs/shared/cms/src/__generated__/index.ts сгенерированный
Просмотреть файл

@ -1,2 +1,2 @@
export * from './fragment-masking';
export * from './gql';
export * from "./fragment-masking";
export * from "./gql";

Просмотреть файл

@ -4,7 +4,6 @@
export * from './lib/cms.error';
export * from './lib/constants';
export * from './lib/factories';
export * from './lib/product-configuration.manager';
export * from './lib/queries/capability-service-by-plan-ids';
export * from './lib/queries/eligibility-content-by-offering';

Просмотреть файл

@ -1,41 +0,0 @@
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
import { ApolloQueryResult, NetworkStatus } from '@apollo/client';
import { faker } from '@faker-js/faker';
import { TypedDocumentNode } from '@graphql-typed-document-node/core';
import { ContentfulErrorResponse } from './types';
/**
* Generates a graphql response from the contentful client based on the passed query.
* Use one of the query factories to provide data for the factory result.
*
* @param query The query to generate a result for
* @param data The result of a QueryFactory matching the query passed
*/
export const ContentfulClientQueryFactory = <Result, Variables>(
query: TypedDocumentNode<Result, Variables>,
data: Result,
override?: ApolloQueryResult<Result>
): ApolloQueryResult<Result> => ({
data: data, // Must be used to negotiate the type inference for Result
loading: false,
networkStatus: NetworkStatus.ready,
...override,
});
export const ContentfulCDNErrorFactory = (
override?: ContentfulErrorResponse
): ContentfulErrorResponse => ({
sys: { type: 'Error', id: faker.string.alpha() },
message: faker.string.alpha(),
requestId: faker.string.uuid(),
...override,
});
export const StrapiEntityFactory = <T>(attributes: T) => {
return {
attributes,
};
};

Просмотреть файл

@ -15,20 +15,16 @@ import {
import { MockFirestoreProvider } from '@fxa/shared/db/firestore';
import { MockStatsDProvider, StatsDService } from '@fxa/shared/metrics/statsd';
import {
CapabilityPurchaseResult,
CapabilityPurchaseResultFactory,
CapabilityServiceByPlanIdsQueryFactory,
CapabilityServiceByPlanIdsResultUtil,
EligibilityContentByOfferingResultUtil,
EligibilityContentByPlanIdsQueryFactory,
EligibilityContentByPlanIdsResultUtil,
EligibilityPurchaseResult,
EligibilityPurchaseResultFactory,
ProductConfigError,
ServicesWithCapabilitiesQueryFactory,
ServicesWithCapabilitiesResultUtil,
StrapiEntity,
StrapiEntityFactory,
} from '../../src';
import { ProductConfigurationManager } from './product-configuration.manager';
import {
@ -88,14 +84,7 @@ describe('productConfigurationManager', () => {
it('should call statsd for incoming events', async () => {
const queryData = EligibilityContentByPlanIdsQueryFactory({
purchases: {
data: [],
meta: {
pagination: {
total: 0,
},
},
},
purchases: [],
});
jest.spyOn(strapiClient.client, 'request').mockResolvedValue(queryData);
jest.spyOn(mockStatsd, 'timing');
@ -139,7 +128,7 @@ describe('productConfigurationManager', () => {
describe('getEligibilityContentByOffering', () => {
it('should return empty result', async () => {
const queryData = EligibilityContentByOfferingQueryFactory({
offerings: { data: [] },
offerings: [],
});
jest.spyOn(strapiClient, 'query').mockResolvedValue(queryData);
@ -154,14 +143,10 @@ describe('productConfigurationManager', () => {
it('should return successfully with results', async () => {
const apiIdentifier = 'test';
const offeringResult = [
StrapiEntityFactory(
EligibilityContentOfferingResultFactory({ apiIdentifier })
),
EligibilityContentOfferingResultFactory({ apiIdentifier }),
];
const queryData = EligibilityContentByOfferingQueryFactory({
offerings: {
data: offeringResult,
},
offerings: offeringResult,
});
jest.spyOn(strapiClient, 'query').mockResolvedValue(queryData);
@ -178,7 +163,7 @@ describe('productConfigurationManager', () => {
describe('getPageContentForOffering', () => {
it('should return empty result', async () => {
const queryData = PageContentForOfferingQueryFactory({
offerings: { data: [], meta: { pagination: { total: 0 } } },
offerings: [],
});
jest.spyOn(strapiClient, 'query').mockResolvedValue(queryData);
@ -190,23 +175,16 @@ describe('productConfigurationManager', () => {
'en'
);
expect(result).toBeInstanceOf(PageContentForOfferingResultUtil);
expect(result.offerings.data).toHaveLength(0);
expect(result.offerings).toHaveLength(0);
});
it('should return successfully with page content for offering', async () => {
const apiIdentifier = 'test';
const offeringResult = [
StrapiEntityFactory(
PageContentOfferingResultFactory({
apiIdentifier,
})
),
];
const offeringResult = PageContentOfferingResultFactory({
apiIdentifier,
});
const queryData = PageContentForOfferingQueryFactory({
offerings: {
data: offeringResult,
meta: { pagination: { total: offeringResult.length } },
},
offerings: [offeringResult],
});
jest.spyOn(strapiClient, 'query').mockResolvedValue(queryData);
@ -218,23 +196,14 @@ describe('productConfigurationManager', () => {
'en'
);
expect(result).toBeInstanceOf(PageContentForOfferingResultUtil);
expect(
result.getOffering().defaultPurchase.data.attributes.purchaseDetails
.data.attributes
).toEqual({
expect(result.getOffering().defaultPurchase.purchaseDetails).toEqual({
...result.purchaseDetailsTransform(
offeringResult[0].attributes.defaultPurchase?.data.attributes
.purchaseDetails.data.attributes
offeringResult.defaultPurchase?.purchaseDetails
),
localizations: {
data: offeringResult[0].attributes.defaultPurchase?.data.attributes.purchaseDetails.data.attributes.localizations.data.map(
(localization) => ({
attributes: result.purchaseDetailsTransform(
localization.attributes
),
})
localizations:
offeringResult.defaultPurchase.purchaseDetails.localizations.map(
(localization) => result.purchaseDetailsTransform(localization)
),
},
});
});
});
@ -242,14 +211,7 @@ describe('productConfigurationManager', () => {
describe('getPurchaseDetailsForEligibility', () => {
it('should return empty result', async () => {
const queryData = EligibilityContentByPlanIdsQueryFactory({
purchases: {
data: [],
meta: {
pagination: {
total: 0,
},
},
},
purchases: [],
});
jest.spyOn(strapiClient, 'query').mockResolvedValue(queryData);
@ -260,27 +222,18 @@ describe('productConfigurationManager', () => {
]);
expect(result).toBeInstanceOf(EligibilityContentByPlanIdsResultUtil);
expect(result.offeringForPlanId('test')).toBeUndefined;
expect(result.purchases.data).toHaveLength(0);
expect(result.purchases).toHaveLength(0);
});
it('should return successfully with subgroups and offering', async () => {
const planId = 'test';
const purchaseResult = [
StrapiEntityFactory(
EligibilityPurchaseResultFactory({
stripePlanChoices: [{ stripePlanChoice: planId }],
})
),
EligibilityPurchaseResultFactory({
stripePlanChoices: [{ stripePlanChoice: planId }],
}),
];
const queryData = EligibilityContentByPlanIdsQueryFactory({
purchases: {
data: purchaseResult,
meta: {
pagination: {
total: purchaseResult.length,
},
},
},
purchases: purchaseResult,
});
jest.spyOn(strapiClient, 'query').mockResolvedValue(queryData);
@ -290,27 +243,17 @@ describe('productConfigurationManager', () => {
'test',
]);
expect(result).toBeInstanceOf(EligibilityContentByPlanIdsResultUtil);
expect(result.offeringForPlanId(planId)?.subGroups.data).toHaveLength(1);
expect(result.offeringForPlanId(planId)?.subGroups).toHaveLength(1);
expect(result.offeringForPlanId(planId)).toBeDefined();
});
it('should return successfully with paging', async () => {
const pageSize = 20;
const purchaseResult: StrapiEntity<EligibilityPurchaseResult>[] = [];
for (let i = 0; i < pageSize + 1; i += 1) {
purchaseResult.push(
StrapiEntityFactory(EligibilityPurchaseResultFactory())
);
}
it('should return successfully', async () => {
const purchaseResult = [
EligibilityPurchaseResultFactory(),
EligibilityPurchaseResultFactory(),
];
const queryData = EligibilityContentByPlanIdsQueryFactory({
purchases: {
data: purchaseResult,
meta: {
pagination: {
total: purchaseResult.length,
},
},
},
purchases: purchaseResult,
});
jest.spyOn(strapiClient, 'query').mockResolvedValue(queryData);
@ -320,21 +263,14 @@ describe('productConfigurationManager', () => {
'test',
]);
expect(result).toBeInstanceOf(EligibilityContentByPlanIdsResultUtil);
expect(strapiClient.query).toBeCalledTimes(2);
expect(strapiClient.query).toBeCalledTimes(1);
});
});
describe('getPurchaseDetailsForCapabilityServiceByPlanId', () => {
it('should return empty result', async () => {
const queryData = CapabilityServiceByPlanIdsQueryFactory({
purchases: {
data: [],
meta: {
pagination: {
total: 0,
},
},
},
purchases: [],
});
jest.spyOn(strapiClient, 'query').mockResolvedValue(queryData);
@ -349,22 +285,11 @@ describe('productConfigurationManager', () => {
it('should return successfully with results', async () => {
const planId = 'test';
const purchaseResult = [
StrapiEntityFactory(
CapabilityPurchaseResultFactory({
stripePlanChoices: [{ stripePlanChoice: planId }],
})
),
];
const purchaseResult = CapabilityPurchaseResultFactory({
stripePlanChoices: [{ stripePlanChoice: planId }],
});
const queryData = CapabilityServiceByPlanIdsQueryFactory({
purchases: {
data: purchaseResult,
meta: {
pagination: {
total: purchaseResult.length,
},
},
},
purchases: [purchaseResult],
});
jest.spyOn(strapiClient, 'query').mockResolvedValue(queryData);
@ -377,23 +302,13 @@ describe('productConfigurationManager', () => {
expect(result.capabilityOfferingForPlanId(planId)).toBeDefined();
});
it('should return successfully with paging', async () => {
const pageSize = 20;
const purchaseResult: StrapiEntity<CapabilityPurchaseResult>[] = [];
for (let i = 0; i < pageSize + 1; i += 1) {
purchaseResult.push(
StrapiEntityFactory(CapabilityPurchaseResultFactory())
);
}
it('should return successfully', async () => {
const purchaseResult = [
CapabilityPurchaseResultFactory(),
CapabilityPurchaseResultFactory(),
];
const queryData = CapabilityServiceByPlanIdsQueryFactory({
purchases: {
data: purchaseResult,
meta: {
pagination: {
total: purchaseResult.length,
},
},
},
purchases: purchaseResult,
});
jest.spyOn(strapiClient, 'query').mockResolvedValue(queryData);
@ -403,23 +318,21 @@ describe('productConfigurationManager', () => {
['test']
);
expect(result).toBeInstanceOf(CapabilityServiceByPlanIdsResultUtil);
expect(strapiClient.query).toBeCalledTimes(2);
expect(strapiClient.query).toBeCalledTimes(1);
});
});
describe('getServicesWithCapabilities', () => {
it('should return results', async () => {
const queryData = ServicesWithCapabilitiesQueryFactory({
services: {
data: [],
},
services: [],
});
jest.spyOn(strapiClient, 'query').mockResolvedValue(queryData);
const result =
await productConfigurationManager.getServicesWithCapabilities();
expect(result).toBeInstanceOf(ServicesWithCapabilitiesResultUtil);
expect(result.services.data).toHaveLength(0);
expect(result.services).toHaveLength(0);
});
it('should return successfully with services and capabilities', async () => {
@ -430,7 +343,7 @@ describe('productConfigurationManager', () => {
const result =
await productConfigurationManager.getServicesWithCapabilities();
expect(result).toBeInstanceOf(ServicesWithCapabilitiesResultUtil);
expect(result.services.data).toHaveLength(1);
expect(result.services).toHaveLength(1);
});
});
@ -438,7 +351,7 @@ describe('productConfigurationManager', () => {
it('should return empty result', async () => {
const queryData =
PurchaseWithDetailsOfferingContentByPlanIdsResultFactory({
purchases: { data: [] },
purchases: [],
});
jest.spyOn(strapiClient, 'query').mockResolvedValue(queryData);
jest.spyOn(strapiClient, 'getLocale').mockResolvedValue('en');
@ -449,13 +362,13 @@ describe('productConfigurationManager', () => {
'en'
);
expect(result).toBeInstanceOf(PurchaseWithDetailsOfferingContentUtil);
expect(result.purchases.data).toHaveLength(0);
expect(result.purchases).toHaveLength(0);
});
it('should return successfully with purchase details and offering', async () => {
const queryData =
PurchaseWithDetailsOfferingContentByPlanIdsResultFactory();
const queryDataItem = queryData.purchases.data[0];
const queryDataItem = queryData.purchases[0];
jest.spyOn(strapiClient, 'query').mockResolvedValue(queryData);
jest.spyOn(strapiClient, 'getLocale').mockResolvedValue('en');
@ -465,31 +378,22 @@ describe('productConfigurationManager', () => {
['test'],
'en'
);
const { stripePlanChoice } =
result.purchases.data[0].attributes.stripePlanChoices?.[0];
const { stripePlanChoice } = result.purchases[0].stripePlanChoices?.[0];
expect(result).toBeInstanceOf(PurchaseWithDetailsOfferingContentUtil);
expect(
result.transformedPurchaseWithCommonContentForPlanId(
stripePlanChoice ?? ''
)?.offering
).toEqual(queryDataItem.attributes.offering);
).toEqual(queryDataItem.offering);
expect(
result.transformedPurchaseWithCommonContentForPlanId(
stripePlanChoice ?? ''
)?.purchaseDetails.data.attributes
)?.purchaseDetails
).toEqual({
...result.purchaseDetailsTransform(
queryDataItem.attributes.purchaseDetails.data.attributes
...result.purchaseDetailsTransform(queryDataItem.purchaseDetails),
localizations: queryDataItem.purchaseDetails.localizations.map(
(localization) => result.purchaseDetailsTransform(localization)
),
localizations: {
data: queryDataItem.attributes.purchaseDetails.data.attributes.localizations.data.map(
(localization) => ({
attributes: result.purchaseDetailsTransform(
localization.attributes
),
})
),
},
});
});
});
@ -500,11 +404,7 @@ describe('productConfigurationManager', () => {
const mockPlan = StripePlanFactory();
const mockOffering = EligibilityContentOfferingResultFactory({
defaultPurchase: {
data: {
attributes: {
stripePlanChoices: [{ stripePlanChoice: mockPlan.id }],
},
},
stripePlanChoices: [{ stripePlanChoice: mockPlan.id }],
},
});
const mockOfferingResult = {} as EligibilityContentByOfferingResultUtil;
@ -528,11 +428,7 @@ describe('productConfigurationManager', () => {
const mockInterval = SubplatInterval.Monthly;
const mockOffering = EligibilityContentOfferingResultFactory({
defaultPurchase: {
data: {
attributes: {
stripePlanChoices: [{ stripePlanChoice: mockPrice.id }],
},
},
stripePlanChoices: [{ stripePlanChoice: mockPrice.id }],
},
});

Просмотреть файл

@ -112,66 +112,39 @@ export class ProductConfigurationManager {
async getPurchaseDetailsForCapabilityServiceByPlanIds(
stripePlanIds: string[]
): Promise<CapabilityServiceByPlanIdsResultUtil> {
let total: number | undefined;
let count = 0;
const queryResults: DeepNonNullable<CapabilityServiceByPlanIdsQuery>[] = [];
const pageSize = 20;
const queryResult = await this.strapiClient.query(
capabilityServiceByPlanIdsQuery,
{
locale: DEFAULT_LOCALE,
stripePlanIds,
}
);
while (total === undefined || count < total) {
const queryResult = (await this.strapiClient.query(
capabilityServiceByPlanIdsQuery,
{
skip: count,
limit: pageSize,
locale: DEFAULT_LOCALE,
stripePlanIds,
}
)) as DeepNonNullable<CapabilityServiceByPlanIdsQuery>;
queryResults.push(queryResult);
count += pageSize;
total = queryResult.purchases.meta.pagination.total;
}
return new CapabilityServiceByPlanIdsResultUtil(queryResults);
return new CapabilityServiceByPlanIdsResultUtil(
queryResult as DeepNonNullable<CapabilityServiceByPlanIdsQuery>
);
}
async getPurchaseDetailsForEligibility(
stripePlanIds: string[]
): Promise<EligibilityContentByPlanIdsResultUtil> {
let total: number | undefined;
let count = 0;
const queryResults: DeepNonNullable<EligibilityContentByPlanIdsQuery>[] =
[];
const pageSize = 20;
const queryResult = await this.strapiClient.query(
eligibilityContentByPlanIdsQuery,
{
locale: DEFAULT_LOCALE,
stripePlanIds,
}
);
while (total === undefined || count < total) {
const queryResult = (await this.strapiClient.query(
eligibilityContentByPlanIdsQuery,
{
skip: count,
limit: pageSize,
locale: DEFAULT_LOCALE,
stripePlanIds,
}
)) as DeepNonNullable<EligibilityContentByPlanIdsQuery>;
queryResults.push(queryResult);
count += pageSize;
total = queryResult.purchases.meta.pagination.total;
}
return new EligibilityContentByPlanIdsResultUtil(queryResults);
return new EligibilityContentByPlanIdsResultUtil(
queryResult as DeepNonNullable<EligibilityContentByPlanIdsQuery>
);
}
async getServicesWithCapabilities(): Promise<ServicesWithCapabilitiesResultUtil> {
const queryResult = await this.strapiClient.query(
servicesWithCapabilitiesQuery,
{
skip: 0,
limit: 100,
locale: DEFAULT_LOCALE,
}
{}
);
return new ServicesWithCapabilitiesResultUtil(
@ -184,30 +157,18 @@ export class ProductConfigurationManager {
acceptLanguage: string
): Promise<PurchaseWithDetailsOfferingContentUtil> {
const locale = await this.strapiClient.getLocale(acceptLanguage);
const queryResults: DeepNonNullable<PurchaseWithDetailsOfferingContentQuery>[] =
[];
const stripePlans: string[][] = [];
// reduce query size by making multiple calls to CMS
for (let i = 0; i < stripePlanIds.length; i += 100) {
stripePlans.push(stripePlanIds.slice(i, i + 100));
}
const queryResult = await this.strapiClient.query(
purchaseWithDetailsOfferingContentQuery,
{
locale,
stripePlanIds,
}
);
while (stripePlans.length > 0) {
const queryResult = (await this.strapiClient.query(
purchaseWithDetailsOfferingContentQuery,
{
skip: 0,
limit: 100,
locale,
stripePlanIds: stripePlans[0],
}
)) as DeepNonNullable<PurchaseWithDetailsOfferingContentQuery>;
queryResults.push(queryResult);
stripePlans.shift();
}
return new PurchaseWithDetailsOfferingContentUtil(queryResults);
return new PurchaseWithDetailsOfferingContentUtil(
queryResult as DeepNonNullable<PurchaseWithDetailsOfferingContentQuery>
);
}
async getOfferingPlanIds(apiIdentifier: string) {
@ -215,10 +176,9 @@ export class ProductConfigurationManager {
apiIdentifier
);
const offering = offeringResult.getOffering();
const planIds =
offering.defaultPurchase.data.attributes.stripePlanChoices.map(
(el) => el.stripePlanChoice
);
const planIds = offering.defaultPurchase.stripePlanChoices.map(
(el) => el.stripePlanChoice
);
return planIds;
}

Просмотреть файл

@ -11,21 +11,12 @@ import {
CapabilityCapabilitiesResult,
CapabilityServicesResult,
} from '.';
import { StrapiEntityFactory } from '../../factories';
export const CapabilityServiceByPlanIdsQueryFactory = (
override?: Partial<CapabilityServiceByPlanIdsQuery>
): CapabilityServiceByPlanIdsQuery => {
const data = [StrapiEntityFactory(CapabilityPurchaseResultFactory())];
return {
purchases: {
meta: {
pagination: {
total: data.length,
},
},
data,
},
purchases: [CapabilityPurchaseResultFactory()],
...override,
};
};
@ -38,9 +29,7 @@ export const CapabilityPurchaseResultFactory = (
stripePlanChoice: faker.string.sample(),
},
],
offering: {
data: StrapiEntityFactory(CapabilityOfferingResultFactory()),
},
offering: CapabilityOfferingResultFactory(),
...override,
});
@ -53,9 +42,7 @@ export const CapabilityOfferingResultFactory = (
stripeLegacyPlan: faker.string.alpha(10),
})
),
capabilities: {
data: [StrapiEntityFactory(CapabilityCapabilitiesResultFactory())],
},
capabilities: [CapabilityCapabilitiesResultFactory()],
...override,
});
@ -63,9 +50,7 @@ export const CapabilityCapabilitiesResultFactory = (
override?: Partial<CapabilityCapabilitiesResult>
): CapabilityCapabilitiesResult => ({
slug: faker.string.sample(),
services: {
data: [StrapiEntityFactory(CapabilityServicesResultFactory())],
},
services: [CapabilityServicesResultFactory()],
...override,
});

Просмотреть файл

@ -5,11 +5,7 @@
import { graphql } from '../../../__generated__/gql';
export const capabilityServiceByPlanIdsQuery = graphql(`
query CapabilityServiceByPlanIds(
$skip: Int!
$limit: Int!
$stripePlanIds: [String]!
) {
query CapabilityServiceByPlanIds($stripePlanIds: [String]!) {
purchases(
filters: {
or: [
@ -21,40 +17,19 @@ export const capabilityServiceByPlanIdsQuery = graphql(`
}
]
}
pagination: { start: $skip, limit: $limit }
pagination: { limit: 200 }
) {
meta {
pagination {
total
}
stripePlanChoices {
stripePlanChoice
}
data {
attributes {
stripePlanChoices {
stripePlanChoice
}
offering {
data {
attributes {
stripeLegacyPlans(pagination: { limit: 200 }) {
stripeLegacyPlan
}
capabilities {
data {
attributes {
slug
services {
data {
attributes {
oauthClientId
}
}
}
}
}
}
}
}
offering {
stripeLegacyPlans(pagination: { limit: 200 }) {
stripeLegacyPlan
}
capabilities {
slug
services {
oauthClientId
}
}
}

Просмотреть файл

@ -2,44 +2,29 @@
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
import { StrapiEntity } from '../../types';
export interface CapabilityServicesResult {
oauthClientId: string;
}
export interface CapabilityCapabilitiesResult {
slug: string;
services: {
data: StrapiEntity<CapabilityServicesResult>[];
};
services: CapabilityServicesResult[];
}
export interface CapabilityOfferingResult {
stripeLegacyPlans: {
stripeLegacyPlan: string;
}[];
capabilities: {
data: StrapiEntity<CapabilityCapabilitiesResult>[];
};
capabilities: CapabilityCapabilitiesResult[];
}
export interface CapabilityPurchaseResult {
stripePlanChoices: {
stripePlanChoice: string;
}[];
offering: {
data: StrapiEntity<CapabilityOfferingResult>;
};
offering: CapabilityOfferingResult;
}
export interface CapabilityServiceByPlanIdsResult {
purchases: {
meta: {
pagination: {
total: number;
};
};
data: StrapiEntity<CapabilityPurchaseResult>[];
};
purchases: CapabilityPurchaseResult[];
}

Просмотреть файл

@ -9,15 +9,12 @@ import { CapabilityServiceByPlanIdsResultUtil } from './util';
describe('CapabilityServiceByPlanIdsResultUtil', () => {
it('should create a util from response', () => {
const result = CapabilityServiceByPlanIdsQueryFactory();
const purchase = result.purchases?.data[0];
const planId = purchase?.attributes?.stripePlanChoices?.[0];
const legacyPlanId =
purchase?.attributes?.offering?.data?.attributes?.stripeLegacyPlans?.[0];
const result2 = CapabilityServiceByPlanIdsQueryFactory();
const util = new CapabilityServiceByPlanIdsResultUtil([
result as CapabilityServiceByPlanIdsResult,
result2 as CapabilityServiceByPlanIdsResult,
]);
const purchase = result.purchases[0];
const planId = purchase?.stripePlanChoices?.[0];
const legacyPlanId = purchase?.offering?.stripeLegacyPlans?.[0];
const util = new CapabilityServiceByPlanIdsResultUtil(
result as CapabilityServiceByPlanIdsResult
);
expect(util).toBeDefined();
expect(

Просмотреть файл

@ -11,20 +11,15 @@ import {
export class CapabilityServiceByPlanIdsResultUtil {
private purchaseByPlanId: Record<string, CapabilityPurchaseResult> = {};
constructor(rawResults: CapabilityServiceByPlanIdsResult[]) {
for (const rawResult of rawResults) {
for (const purchase of rawResult.purchases.data) {
purchase.attributes.stripePlanChoices?.forEach(
({ stripePlanChoice }) => {
this.purchaseByPlanId[stripePlanChoice] = purchase.attributes;
}
);
constructor(rawResult: CapabilityServiceByPlanIdsResult) {
for (const purchase of rawResult.purchases) {
for (const stripePlanChoice of purchase.stripePlanChoices ?? []) {
this.purchaseByPlanId[stripePlanChoice.stripePlanChoice] = purchase;
}
purchase.attributes.offering.data.attributes.stripeLegacyPlans?.forEach(
({ stripeLegacyPlan }) => {
this.purchaseByPlanId[stripeLegacyPlan] = purchase.attributes;
}
);
for (const stripeLegacyPlan of purchase.offering.stripeLegacyPlans ??
[]) {
this.purchaseByPlanId[stripeLegacyPlan.stripeLegacyPlan] = purchase;
}
}
}
@ -32,6 +27,6 @@ export class CapabilityServiceByPlanIdsResultUtil {
capabilityOfferingForPlanId(
planId: string
): CapabilityOfferingResult | undefined {
return this.purchaseByPlanId[planId]?.offering.data.attributes;
return this.purchaseByPlanId[planId]?.offering;
}
}

Просмотреть файл

@ -11,15 +11,12 @@ import {
EligibilityContentSubgroupResult,
EligibilityContentByOfferingResult,
} from '.';
import { StrapiEntityFactory } from '../../factories';
export const EligibilityContentByOfferingQueryFactory = (
override?: Partial<EligibilityContentByOfferingQuery>
): EligibilityContentByOfferingQuery => {
return {
offerings: {
data: [StrapiEntityFactory(EligibilityContentOfferingResultFactory())],
},
offerings: [EligibilityContentOfferingResultFactory()],
...override,
};
};
@ -28,9 +25,7 @@ export const EligibilityContentByOfferingResultFactory = (
override?: Partial<EligibilityContentByOfferingResult>
): EligibilityContentByOfferingResult => {
return {
offerings: {
data: [StrapiEntityFactory(EligibilityContentOfferingResultFactory())],
},
offerings: [EligibilityContentOfferingResultFactory()],
...override,
};
};
@ -41,17 +36,13 @@ export const EligibilityContentOfferingResultFactory = (
apiIdentifier: faker.string.sample(),
stripeProductId: faker.string.sample(),
defaultPurchase: {
data: StrapiEntityFactory({
stripePlanChoices: [
{
stripePlanChoice: faker.string.sample(),
},
],
}),
},
subGroups: {
data: [StrapiEntityFactory(EligibilityContentSubgroupResultFactory())],
stripePlanChoices: [
{
stripePlanChoice: faker.string.sample(),
},
],
},
subGroups: [EligibilityContentSubgroupResultFactory()],
...override,
});
@ -59,23 +50,7 @@ export const EligibilityContentSubgroupResultFactory = (
override?: Partial<EligibilityContentSubgroupResult>
): EligibilityContentSubgroupResult => ({
groupName: faker.string.sample(),
offerings: {
data: [
StrapiEntityFactory({
apiIdentifier: faker.string.sample(),
stripeProductId: faker.string.sample(),
defaultPurchase: {
data: StrapiEntityFactory({
stripePlanChoices: [
{
stripePlanChoice: faker.string.sample(),
},
],
}),
},
}),
],
},
offerings: [EligibilityContentSubgroupOfferingResultFactory()],
...override,
});
@ -85,13 +60,11 @@ export const EligibilityContentSubgroupOfferingResultFactory = (
apiIdentifier: faker.string.sample(),
stripeProductId: faker.string.sample(),
defaultPurchase: {
data: StrapiEntityFactory({
stripePlanChoices: [
{
stripePlanChoice: faker.string.sample(),
},
],
}),
stripePlanChoices: [
{
stripePlanChoice: faker.string.sample(),
},
],
},
...override,
});

Просмотреть файл

@ -7,44 +7,24 @@ import { graphql } from '../../../__generated__/gql';
export const eligibilityContentByOfferingQuery = graphql(`
query EligibilityContentByOffering($apiIdentifier: String!) {
offerings(
pagination: { start: 0, limit: 2 }
filters: { apiIdentifier: { eq: $apiIdentifier } }
pagination: { limit: 200 }
) {
data {
attributes {
apiIdentifier
stripeProductId
defaultPurchase {
stripePlanChoices {
stripePlanChoice
}
}
subGroups {
groupName
offerings {
apiIdentifier
stripeProductId
defaultPurchase {
data {
attributes {
stripePlanChoices {
stripePlanChoice
}
}
}
}
subGroups {
data {
attributes {
groupName
offerings {
data {
attributes {
apiIdentifier
stripeProductId
defaultPurchase {
data {
attributes {
stripePlanChoices {
stripePlanChoice
}
}
}
}
}
}
}
}
stripePlanChoices {
stripePlanChoice
}
}
}

Просмотреть файл

@ -2,43 +2,32 @@
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
import { StrapiEntity } from '../../types';
export interface EligibilityContentSubgroupOfferingResult {
apiIdentifier: string;
stripeProductId: string;
defaultPurchase: {
data: StrapiEntity<{
stripePlanChoices: {
stripePlanChoice: string;
}[];
}>;
stripePlanChoices: {
stripePlanChoice: string;
}[];
};
}
export interface EligibilityContentSubgroupResult {
groupName: string;
offerings: {
data: StrapiEntity<EligibilityContentSubgroupOfferingResult>[];
};
offerings: EligibilityContentSubgroupOfferingResult[];
}
export interface EligibilityContentOfferingResult {
apiIdentifier: string;
stripeProductId: string;
defaultPurchase: {
data: StrapiEntity<{
stripePlanChoices: {
stripePlanChoice: string;
}[];
}>;
};
subGroups: {
data: StrapiEntity<EligibilityContentSubgroupResult>[];
stripePlanChoices: {
stripePlanChoice: string;
}[];
};
subGroups: EligibilityContentSubgroupResult[];
}
export interface EligibilityContentByOfferingResult {
offerings: {
data: StrapiEntity<EligibilityContentOfferingResult>[];
};
offerings: EligibilityContentOfferingResult[];
}

Просмотреть файл

@ -8,7 +8,6 @@ import {
EligibilityContentByOfferingResultUtil,
EligibilityContentOfferingResultFactory,
} from '.';
import { StrapiEntityFactory } from '../../factories';
describe('EligibilityByOfferingResultUtil', () => {
it('should create a util from response', () => {
@ -18,12 +17,12 @@ describe('EligibilityByOfferingResultUtil', () => {
);
expect(util).toBeDefined();
expect(util.getOffering()).toBeDefined();
expect(util.offerings.data).toHaveLength(1);
expect(util.offerings).toHaveLength(1);
});
it('returns empty if no offering is returned', () => {
const result = EligibilityContentByOfferingQueryFactory({
offerings: { data: [] },
offerings: [],
});
const util = new EligibilityContentByOfferingResultUtil(
result as EligibilityContentByOfferingResult
@ -34,12 +33,12 @@ describe('EligibilityByOfferingResultUtil', () => {
});
it('throws error if more than offering is returned', () => {
const data = [
StrapiEntityFactory(EligibilityContentOfferingResultFactory()),
StrapiEntityFactory(EligibilityContentOfferingResultFactory()),
const offerings = [
EligibilityContentOfferingResultFactory(),
EligibilityContentOfferingResultFactory(),
];
const result = EligibilityContentByOfferingQueryFactory({
offerings: { data },
offerings,
});
const util = new EligibilityContentByOfferingResultUtil(
result as EligibilityContentByOfferingResult

Просмотреть файл

@ -11,11 +11,11 @@ export class EligibilityContentByOfferingResultUtil {
constructor(private rawResult: EligibilityContentByOfferingResult) {}
getOffering(): EligibilityContentOfferingResult {
const offering = this.offerings.data.at(0);
const offering = this.offerings.at(0);
if (!offering) throw Error('getOffering - No offering exists');
if (this.offerings.data.length > 1)
if (this.offerings.length > 1)
throw Error('getOffering - More than one offering');
return offering.attributes;
return offering;
}
get offerings(): EligibilityContentByOfferingResult['offerings'] {

Просмотреть файл

@ -12,21 +12,12 @@ import {
EligibilitySubgroupResult,
type EligibilityContentByPlanIdsResult,
} from '.';
import { StrapiEntityFactory } from '../../factories';
export const EligibilityContentByPlanIdsQueryFactory = (
override?: Partial<EligibilityContentByPlanIdsQuery>
): EligibilityContentByPlanIdsQuery => {
const data = [StrapiEntityFactory(EligibilityPurchaseResultFactory())];
return {
purchases: {
meta: {
pagination: {
total: data.length,
},
},
data,
},
purchases: [EligibilityPurchaseResultFactory()],
...override,
};
};
@ -34,16 +25,8 @@ export const EligibilityContentByPlanIdsQueryFactory = (
export const EligibilityContentByPlanIdsResultFactory = (
override?: Partial<EligibilityContentByPlanIdsResult>
): EligibilityContentByPlanIdsResult => {
const data = [StrapiEntityFactory(EligibilityPurchaseResultFactory())];
return {
purchases: {
meta: {
pagination: {
total: data.length,
},
},
data,
},
purchases: [EligibilityPurchaseResultFactory()],
...override,
};
};
@ -56,9 +39,7 @@ export const EligibilityPurchaseResultFactory = (
stripePlanChoice: faker.string.sample(),
},
],
offering: {
data: StrapiEntityFactory(EligibilityOfferingResultFactory()),
},
offering: EligibilityOfferingResultFactory(),
...override,
});
@ -73,9 +54,7 @@ export const EligibilityOfferingResultFactory = (
})
),
countries: [faker.string.sample()],
subGroups: {
data: [StrapiEntityFactory(EligibilitySubgroupResultFactory())],
},
subGroups: [EligibilitySubgroupResultFactory()],
...override,
});
@ -83,9 +62,7 @@ export const EligibilitySubgroupResultFactory = (
override?: Partial<EligibilitySubgroupResult>
): EligibilitySubgroupResult => ({
groupName: faker.string.sample(),
offerings: {
data: [StrapiEntityFactory(EligibilitySubgroupOfferingResultFactory())],
},
offerings: [EligibilitySubgroupOfferingResultFactory()],
...override,
});

Просмотреть файл

@ -5,13 +5,8 @@
import { graphql } from '../../../__generated__/gql';
export const eligibilityContentByPlanIdsQuery = graphql(`
query EligibilityContentByPlanIds(
$skip: Int!
$limit: Int!
$stripePlanIds: [String]!
) {
query EligibilityContentByPlanIds($stripePlanIds: [String]!) {
purchases(
pagination: { start: $skip, limit: $limit }
filters: {
or: [
{ stripePlanChoices: { stripePlanChoice: { in: $stripePlanIds } } }
@ -22,45 +17,25 @@ export const eligibilityContentByPlanIdsQuery = graphql(`
}
]
}
pagination: { limit: 200 }
) {
meta {
pagination {
total
}
stripePlanChoices {
stripePlanChoice
}
data {
attributes {
stripePlanChoices {
stripePlanChoice
}
offering {
data {
attributes {
stripeProductId
stripeLegacyPlans(pagination: { limit: 200 }) {
stripeLegacyPlan
}
countries
subGroups {
data {
attributes {
groupName
offerings {
data {
attributes {
stripeProductId
stripeLegacyPlans(pagination: { limit: 200 }) {
stripeLegacyPlan
}
countries
}
}
}
}
}
}
}
offering {
stripeProductId
stripeLegacyPlans(pagination: { limit: 200 }) {
stripeLegacyPlan
}
countries
subGroups {
groupName
offerings {
stripeProductId
stripeLegacyPlans(pagination: { limit: 200 }) {
stripeLegacyPlan
}
countries
}
}
}

Просмотреть файл

@ -2,8 +2,6 @@
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
import { StrapiEntity } from '../../types';
export interface EligibilitySubgroupOfferingResult {
stripeProductId: string;
stripeLegacyPlans: {
@ -14,9 +12,7 @@ export interface EligibilitySubgroupOfferingResult {
export interface EligibilitySubgroupResult {
groupName: string;
offerings: {
data: StrapiEntity<EligibilitySubgroupOfferingResult>[];
};
offerings: EligibilitySubgroupOfferingResult[];
}
export interface EligibilityOfferingResult {
@ -25,27 +21,16 @@ export interface EligibilityOfferingResult {
stripeLegacyPlan: string;
}[];
countries: string[];
subGroups: {
data: StrapiEntity<EligibilitySubgroupResult>[];
};
subGroups: EligibilitySubgroupResult[];
}
export interface EligibilityPurchaseResult {
stripePlanChoices: {
stripePlanChoice: string;
}[];
offering: {
data: StrapiEntity<EligibilityOfferingResult>;
};
offering: EligibilityOfferingResult;
}
export interface EligibilityContentByPlanIdsResult {
purchases: {
meta: {
pagination: {
total: number;
};
};
data: StrapiEntity<EligibilityPurchaseResult>[];
};
purchases: EligibilityPurchaseResult[];
}

Просмотреть файл

@ -11,13 +11,12 @@ import {
describe('EligibilityContentByPlanIdsResultUtil', () => {
it('should create a util from response', () => {
const result = EligibilityContentByPlanIdsQueryFactory();
const purchase = result.purchases?.data[0];
const planId = purchase?.attributes?.stripePlanChoices?.[0];
const legacyPlanId =
purchase?.attributes?.offering?.data?.attributes?.stripeLegacyPlans?.[0];
const util = new EligibilityContentByPlanIdsResultUtil([
result as EligibilityContentByPlanIdsResult,
]);
const purchase = result.purchases[0];
const planId = purchase?.stripePlanChoices?.[0];
const legacyPlanId = purchase?.offering?.stripeLegacyPlans?.[0];
const util = new EligibilityContentByPlanIdsResultUtil(
result as EligibilityContentByPlanIdsResult
);
expect(util).toBeDefined();
expect(
util.offeringForPlanId(planId?.stripePlanChoice ?? '')?.stripeProductId
@ -26,6 +25,6 @@ describe('EligibilityContentByPlanIdsResultUtil', () => {
util.offeringForPlanId(legacyPlanId?.stripeLegacyPlan ?? '')
?.stripeProductId
).toBeDefined();
expect(util.purchases.data.length).toBe(1);
expect(util.purchases.length).toBe(1);
});
});

Просмотреть файл

@ -11,45 +11,23 @@ import {
export class EligibilityContentByPlanIdsResultUtil {
private purchaseByPlanId: Record<string, EligibilityPurchaseResult> = {};
constructor(private rawResults: EligibilityContentByPlanIdsResult[]) {
for (const rawResult of rawResults) {
for (const purchase of rawResult.purchases.data) {
purchase.attributes.stripePlanChoices?.forEach(
({ stripePlanChoice }) => {
this.purchaseByPlanId[stripePlanChoice] = purchase.attributes;
}
);
constructor(private rawResult: EligibilityContentByPlanIdsResult) {
for (const purchase of rawResult.purchases) {
purchase.stripePlanChoices?.forEach(({ stripePlanChoice }) => {
this.purchaseByPlanId[stripePlanChoice] = purchase;
});
purchase.attributes.offering.data.attributes.stripeLegacyPlans?.forEach(
({ stripeLegacyPlan }) => {
this.purchaseByPlanId[stripeLegacyPlan] = purchase.attributes;
}
);
}
purchase.offering.stripeLegacyPlans?.forEach(({ stripeLegacyPlan }) => {
this.purchaseByPlanId[stripeLegacyPlan] = purchase;
});
}
}
offeringForPlanId(planId: string): EligibilityOfferingResult | undefined {
return this.purchaseByPlanId[planId]?.offering.data.attributes;
return this.purchaseByPlanId[planId]?.offering;
}
get purchases(): EligibilityContentByPlanIdsResult['purchases'] {
return {
meta: {
pagination: {
total: this.rawResults
.map((rawResult) => rawResult.purchases.meta.pagination.total)
.reduce((acc, curr) => acc + curr, 0),
},
},
data: [
...new Map(
this.rawResults
.map((rawResult) => rawResult.purchases.data)
.flat()
.map((res) => [JSON.stringify(res), res])
).values(),
],
};
get purchases(): EligibilityPurchaseResult[] {
return this.rawResult.purchases;
}
}

Просмотреть файл

@ -5,14 +5,11 @@
import { faker } from '@faker-js/faker';
import { Locale, LocalesResult } from '.';
import { StrapiEntityFactory } from '../../factories';
export const LocalesResultFactory = (
override?: Partial<LocalesResult>
): LocalesResult => ({
i18NLocales: {
data: [StrapiEntityFactory(LocaleFactory())],
},
i18NLocales: [LocaleFactory()],
...override,
});

Просмотреть файл

@ -7,11 +7,7 @@ import { graphql } from '../../../__generated__/gql';
export const localesQuery = graphql(`
query Locales {
i18NLocales {
data {
attributes {
code
}
}
code
}
}
`);

Просмотреть файл

@ -2,14 +2,10 @@
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
import { StrapiEntity } from '../../types';
export interface Locale {
code: string;
}
export interface LocalesResult {
i18NLocales: {
data: StrapiEntity<Locale>[];
};
i18NLocales: Locale[];
}

Просмотреть файл

@ -10,14 +10,11 @@ import {
OfferingDefaultPurchaseResult,
OfferingResult,
} from '.';
import { StrapiEntityFactory } from '../../factories';
export const OfferingQueryFactory = (
override?: Partial<OfferingQuery>
): OfferingQuery => ({
offering: {
data: StrapiEntityFactory(OfferingResultFactory()),
},
offering: OfferingResultFactory(),
...override,
});
@ -27,9 +24,7 @@ export const OfferingResultFactory = (
return {
stripeProductId: faker.string.sample(),
countries: [faker.string.sample()],
defaultPurchase: {
data: StrapiEntityFactory(OfferingDefaultPurchaseResultFactory()),
},
defaultPurchase: OfferingDefaultPurchaseResultFactory(),
...override,
};
};
@ -38,12 +33,8 @@ export const OfferingDefaultPurchaseResultFactory = (
override?: Partial<OfferingDefaultPurchaseResult>
): OfferingDefaultPurchaseResult => ({
purchaseDetails: {
data: StrapiEntityFactory({
...OfferingPurchaseResultFactory(),
localizations: {
data: [StrapiEntityFactory(OfferingPurchaseResultFactory())],
},
}),
...OfferingPurchaseResultFactory(),
localizations: [OfferingPurchaseResultFactory()],
},
...override,
});

Просмотреть файл

@ -6,36 +6,20 @@ import { graphql } from '../../../__generated__/gql';
export const offeringQuery = graphql(`
query Offering($id: ID!, $locale: String!) {
offering(id: $id) {
data {
attributes {
stripeProductId
countries
defaultPurchase {
data {
attributes {
purchaseDetails {
data {
attributes {
productName
details
subtitle
webIcon
localizations(filters: { locale: { eq: $locale } }) {
data {
attributes {
productName
details
subtitle
webIcon
}
}
}
}
}
}
}
}
offering(documentId: $id) {
stripeProductId
countries
defaultPurchase {
purchaseDetails {
productName
details
subtitle
webIcon
localizations(filters: { locale: { eq: $locale } }) {
productName
details
subtitle
webIcon
}
}
}

Просмотреть файл

@ -2,8 +2,6 @@
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
import { StrapiEntity } from '../../types';
export interface OfferingPurchaseResult {
productName: string;
details: string;
@ -12,21 +10,13 @@ export interface OfferingPurchaseResult {
}
export interface OfferingDefaultPurchaseResult {
purchaseDetails: {
data: StrapiEntity<
OfferingPurchaseResult & {
localizations: {
data: StrapiEntity<OfferingPurchaseResult>[];
};
}
>;
purchaseDetails: OfferingPurchaseResult & {
localizations: OfferingPurchaseResult[];
};
}
export interface OfferingResult {
stripeProductId: string;
countries: string[];
defaultPurchase: {
data: StrapiEntity<OfferingDefaultPurchaseResult>;
};
defaultPurchase: OfferingDefaultPurchaseResult;
}

Просмотреть файл

@ -15,19 +15,11 @@ import {
PageContentPurchaseDetailsResult,
PageContentPurchaseDetailsTransformed,
} from '.';
import { StrapiEntityFactory } from '../../factories';
export const PageContentForOfferingQueryFactory = (
override?: Partial<PageContentForOfferingQuery>
): PageContentForOfferingQuery => ({
offerings: {
meta: {
pagination: {
total: 1,
},
},
data: [StrapiEntityFactory(PageContentOfferingResultFactory())],
},
offerings: [PageContentOfferingResultFactory()],
...override,
});
@ -35,12 +27,8 @@ export const PageContentOfferingDefaultPurchaseResultFactory = (
override?: Partial<PageContentOfferingDefaultPurchaseResult>
): PageContentOfferingDefaultPurchaseResult => ({
purchaseDetails: {
data: StrapiEntityFactory({
...PageContentPurchaseDetailsResultFactory(),
localizations: {
data: [StrapiEntityFactory(PageContentPurchaseDetailsResultFactory())],
},
}),
...PageContentPurchaseDetailsResultFactory(),
localizations: [PageContentPurchaseDetailsResultFactory()],
},
...override,
});
@ -49,14 +37,8 @@ export const PageContentOfferingDefaultPurchaseTransformedFactory = (
override?: Partial<PageContentOfferingDefaultPurchaseTransformed>
): PageContentOfferingDefaultPurchaseTransformed => ({
purchaseDetails: {
data: StrapiEntityFactory({
...PageContentPurchaseDetailsTransformedFactory(),
localizations: {
data: [
StrapiEntityFactory(PageContentPurchaseDetailsTransformedFactory()),
],
},
}),
...PageContentPurchaseDetailsTransformedFactory(),
localizations: [PageContentPurchaseDetailsTransformedFactory()],
},
...override,
});
@ -66,25 +48,10 @@ export const PageContentOfferingResultFactory = (
): PageContentOfferingResult => ({
apiIdentifier: faker.string.sample(),
stripeProductId: faker.string.sample(),
defaultPurchase: {
data: StrapiEntityFactory({
...PageContentOfferingDefaultPurchaseResultFactory(),
localizations: {
data: [
StrapiEntityFactory(
PageContentOfferingDefaultPurchaseResultFactory()
),
],
},
}),
},
defaultPurchase: PageContentOfferingDefaultPurchaseResultFactory(),
commonContent: {
data: StrapiEntityFactory({
...PageContentCommonContentResultFactory(),
localizations: {
data: [StrapiEntityFactory(PageContentCommonContentResultFactory())],
},
}),
...PageContentCommonContentResultFactory(),
localizations: [PageContentCommonContentResultFactory()],
},
...override,
});
@ -93,18 +60,7 @@ export const PageContentOfferingTransformedFactory = (
override?: Partial<PageContentOfferingTransformed>
): PageContentOfferingTransformed => ({
...PageContentOfferingResultFactory(),
defaultPurchase: {
data: StrapiEntityFactory({
...PageContentOfferingDefaultPurchaseTransformedFactory(),
localizations: {
data: [
StrapiEntityFactory(
PageContentOfferingDefaultPurchaseTransformedFactory()
),
],
},
}),
},
defaultPurchase: PageContentOfferingDefaultPurchaseTransformedFactory(),
...override,
});

Просмотреть файл

@ -7,76 +7,47 @@ import { graphql } from '../../../__generated__/gql';
export const pageContentForOfferingQuery = graphql(`
query PageContentForOffering($locale: String!, $apiIdentifier: String!) {
offerings(
pagination: { start: 0, limit: 2 }
filters: { apiIdentifier: { eq: $apiIdentifier } }
pagination: { limit: 200 }
) {
meta {
pagination {
total
apiIdentifier
stripeProductId
defaultPurchase {
purchaseDetails {
details
productName
subtitle
webIcon
localizations(filters: { locale: { eq: $locale } }) {
details
productName
subtitle
webIcon
}
}
}
data {
attributes {
apiIdentifier
stripeProductId
defaultPurchase {
data {
attributes {
purchaseDetails {
data {
attributes {
details
productName
subtitle
webIcon
localizations(filters: { locale: { eq: $locale } }) {
data {
attributes {
details
productName
subtitle
webIcon
}
}
}
}
}
}
}
}
}
commonContent {
data {
attributes {
privacyNoticeUrl
privacyNoticeDownloadUrl
termsOfServiceUrl
termsOfServiceDownloadUrl
cancellationUrl
emailIcon
successActionButtonUrl
successActionButtonLabel
newsletterLabelTextCode
newsletterSlug
localizations(filters: { locale: { eq: $locale } }) {
data {
attributes {
privacyNoticeUrl
privacyNoticeDownloadUrl
termsOfServiceUrl
termsOfServiceDownloadUrl
cancellationUrl
emailIcon
successActionButtonUrl
successActionButtonLabel
newsletterLabelTextCode
newsletterSlug
}
}
}
}
}
}
commonContent {
privacyNoticeUrl
privacyNoticeDownloadUrl
termsOfServiceUrl
termsOfServiceDownloadUrl
cancellationUrl
emailIcon
successActionButtonUrl
successActionButtonLabel
newsletterLabelTextCode
newsletterSlug
localizations(filters: { locale: { eq: $locale } }) {
privacyNoticeUrl
privacyNoticeDownloadUrl
termsOfServiceUrl
termsOfServiceDownloadUrl
cancellationUrl
emailIcon
successActionButtonUrl
successActionButtonLabel
newsletterLabelTextCode
newsletterSlug
}
}
}

Просмотреть файл

@ -2,8 +2,6 @@
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
import { StrapiEntity } from '../../types';
export interface PageContentCommonContentResult {
privacyNoticeUrl: string;
privacyNoticeDownloadUrl: string;
@ -30,60 +28,31 @@ export interface PageContentPurchaseDetailsTransformed
}
export interface PageContentOfferingDefaultPurchaseResult {
purchaseDetails: {
data: StrapiEntity<
PageContentPurchaseDetailsResult & {
localizations: {
data: StrapiEntity<PageContentPurchaseDetailsResult>[];
};
}
>;
purchaseDetails: PageContentPurchaseDetailsResult & {
localizations: PageContentPurchaseDetailsResult[];
};
}
export interface PageContentOfferingDefaultPurchaseTransformed {
purchaseDetails: {
data: StrapiEntity<
PageContentPurchaseDetailsTransformed & {
localizations: {
data: StrapiEntity<PageContentPurchaseDetailsTransformed>[];
};
}
>;
purchaseDetails: PageContentPurchaseDetailsTransformed & {
localizations: PageContentPurchaseDetailsTransformed[];
};
}
export interface PageContentOfferingTransformed
extends Omit<PageContentOfferingResult, 'defaultPurchase'> {
defaultPurchase: {
data: StrapiEntity<PageContentOfferingDefaultPurchaseTransformed>;
};
defaultPurchase: PageContentOfferingDefaultPurchaseTransformed;
}
export interface PageContentOfferingResult {
apiIdentifier: string;
stripeProductId: string;
defaultPurchase: {
data: StrapiEntity<PageContentOfferingDefaultPurchaseResult>;
};
commonContent: {
data: StrapiEntity<
PageContentCommonContentResult & {
localizations: {
data: StrapiEntity<PageContentCommonContentResult>[];
};
}
>;
defaultPurchase: PageContentOfferingDefaultPurchaseResult;
commonContent: PageContentCommonContentResult & {
localizations: PageContentCommonContentResult[];
};
}
export interface PageContentForOfferingResult {
offerings: {
meta: {
pagination: {
total: number;
};
};
data: StrapiEntity<PageContentOfferingResult>[];
};
offerings: PageContentOfferingResult[];
}

Просмотреть файл

@ -16,7 +16,7 @@ describe('PageContentForOfferingUtil', () => {
result as PageContentForOfferingResult
);
expect(util).toBeDefined();
expect(util.offerings.data).toHaveLength(1);
expect(util.offerings).toHaveLength(1);
});
describe('transformPageContentPurchaseDetails', () => {

Просмотреть файл

@ -17,36 +17,22 @@ export class PageContentForOfferingResultUtil {
}
getOffering(): PageContentOfferingTransformed {
const offering = this.offerings.data.at(0);
const offering = this.offerings.at(0);
if (!offering) throw Error('getOffering - No offering exists');
if (this.offerings.data.length > 1)
if (this.offerings.length > 1)
throw Error('getOffering - More than one offering');
return {
...offering.attributes,
...offering,
defaultPurchase: {
data: {
attributes: {
purchaseDetails: {
data: {
attributes: {
...this.purchaseDetailsTransform(
offering.attributes.defaultPurchase.data.attributes
.purchaseDetails.data.attributes
),
localizations: {
data: offering.attributes.defaultPurchase.data.attributes.purchaseDetails.data.attributes.localizations.data.map(
(localization) => ({
attributes: this.purchaseDetailsTransform(
localization.attributes
),
})
),
},
},
},
},
},
purchaseDetails: {
...this.purchaseDetailsTransform(
offering.defaultPurchase.purchaseDetails
),
localizations:
offering.defaultPurchase.purchaseDetails.localizations.map(
(localization) => this.purchaseDetailsTransform(localization)
),
},
},
};

Просмотреть файл

@ -11,7 +11,6 @@ import {
PurchaseWithDetailsOfferingContentResult,
PurchaseWithDetailsOfferingContentTransformed,
} from './types';
import { StrapiEntityFactory } from '../../factories';
export const PurchaseDetailsResultFactory = (
override?: Partial<PurchaseDetailsResult>
@ -69,12 +68,8 @@ export const PurchaseOfferingResultFactory = (
})
),
commonContent: {
data: StrapiEntityFactory({
...OfferingCommonContentResultFactory(),
localizations: {
data: [StrapiEntityFactory(OfferingCommonContentResultFactory())],
},
}),
...OfferingCommonContentResultFactory(),
localizations: [OfferingCommonContentResultFactory()],
},
...override,
});
@ -89,16 +84,10 @@ export const PurchaseWithDetailsOfferingContentResultFactory = (
})
),
purchaseDetails: {
data: StrapiEntityFactory({
...PurchaseDetailsResultFactory(),
localizations: {
data: [StrapiEntityFactory(PurchaseDetailsResultFactory())],
},
}),
},
offering: {
data: StrapiEntityFactory(PurchaseOfferingResultFactory()),
...PurchaseDetailsResultFactory(),
localizations: [PurchaseDetailsResultFactory()],
},
offering: PurchaseOfferingResultFactory(),
...override,
});
@ -107,12 +96,8 @@ export const PurchaseWithDetailsOfferingContentTransformedFactory = (
): PurchaseWithDetailsOfferingContentTransformed => ({
...PurchaseWithDetailsOfferingContentResultFactory(),
purchaseDetails: {
data: StrapiEntityFactory({
...PurchaseDetailsTransformedFactory(),
localizations: {
data: [StrapiEntityFactory(PurchaseDetailsTransformedFactory())],
},
}),
...PurchaseDetailsTransformedFactory(),
localizations: [PurchaseDetailsTransformedFactory()],
},
...override,
});
@ -120,10 +105,6 @@ export const PurchaseWithDetailsOfferingContentTransformedFactory = (
export const PurchaseWithDetailsOfferingContentByPlanIdsResultFactory = (
override?: Partial<PurchaseWithDetailsOfferingContentByPlanIdsResult>
): PurchaseWithDetailsOfferingContentByPlanIdsResult => ({
purchases: {
data: [
StrapiEntityFactory(PurchaseWithDetailsOfferingContentResultFactory()),
],
},
purchases: [PurchaseWithDetailsOfferingContentResultFactory()],
...override,
});

Просмотреть файл

@ -5,13 +5,10 @@ import { graphql } from '../../../__generated__/gql';
export const purchaseWithDetailsOfferingContentQuery = graphql(`
query PurchaseWithDetailsOfferingContent(
$skip: Int!
$limit: Int!
$locale: String!
$stripePlanIds: [String]!
) {
purchases(
pagination: { start: $skip, limit: $limit }
filters: {
or: [
{ stripePlanChoices: { stripePlanChoice: { in: $stripePlanIds } } }
@ -22,73 +19,50 @@ export const purchaseWithDetailsOfferingContentQuery = graphql(`
}
]
}
pagination: { limit: 500 }
) {
data {
attributes {
stripePlanChoices {
stripePlanChoice
}
purchaseDetails {
data {
attributes {
details
productName
subtitle
webIcon
localizations(filters: { locale: { eq: $locale } }) {
data {
attributes {
details
productName
subtitle
webIcon
}
}
}
}
}
}
offering {
data {
attributes {
stripeProductId
stripeLegacyPlans(pagination: { limit: 200 }) {
stripeLegacyPlan
}
commonContent {
data {
attributes {
privacyNoticeUrl
privacyNoticeDownloadUrl
termsOfServiceUrl
termsOfServiceDownloadUrl
cancellationUrl
emailIcon
successActionButtonUrl
successActionButtonLabel
newsletterLabelTextCode
newsletterSlug
localizations(filters: { locale: { eq: $locale } }) {
data {
attributes {
privacyNoticeUrl
privacyNoticeDownloadUrl
termsOfServiceUrl
termsOfServiceDownloadUrl
cancellationUrl
emailIcon
successActionButtonUrl
successActionButtonLabel
newsletterLabelTextCode
newsletterSlug
}
}
}
}
}
}
}
}
stripePlanChoices {
stripePlanChoice
}
purchaseDetails {
details
productName
subtitle
webIcon
localizations(filters: { locale: { eq: $locale } }) {
details
productName
subtitle
webIcon
}
}
offering {
stripeProductId
stripeLegacyPlans(pagination: { limit: 200 }) {
stripeLegacyPlan
}
commonContent {
privacyNoticeUrl
privacyNoticeDownloadUrl
termsOfServiceUrl
termsOfServiceDownloadUrl
cancellationUrl
emailIcon
successActionButtonUrl
successActionButtonLabel
newsletterLabelTextCode
newsletterSlug
localizations(filters: { locale: { eq: $locale } }) {
privacyNoticeUrl
privacyNoticeDownloadUrl
termsOfServiceUrl
termsOfServiceDownloadUrl
cancellationUrl
emailIcon
successActionButtonUrl
successActionButtonLabel
newsletterLabelTextCode
newsletterSlug
}
}
}

Просмотреть файл

@ -2,8 +2,6 @@
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
import { StrapiEntity } from '../../types';
export interface PurchaseDetailsResult {
details: string;
productName: string;
@ -34,14 +32,8 @@ export interface PurchaseOfferingResult {
stripeLegacyPlans: {
stripeLegacyPlan: string;
}[];
commonContent: {
data: StrapiEntity<
OfferingCommonContentResult & {
localizations: {
data: StrapiEntity<OfferingCommonContentResult>[];
};
}
>;
commonContent: OfferingCommonContentResult & {
localizations: OfferingCommonContentResult[];
};
}
@ -49,35 +41,19 @@ export interface PurchaseWithDetailsOfferingContentResult {
stripePlanChoices: {
stripePlanChoice: string;
}[];
purchaseDetails: {
data: StrapiEntity<
PurchaseDetailsResult & {
localizations: {
data: StrapiEntity<PurchaseDetailsResult>[];
};
}
>;
};
offering: {
data: StrapiEntity<PurchaseOfferingResult>;
purchaseDetails: PurchaseDetailsResult & {
localizations: PurchaseDetailsResult[];
};
offering: PurchaseOfferingResult;
}
export interface PurchaseWithDetailsOfferingContentTransformed
extends Omit<PurchaseWithDetailsOfferingContentResult, 'purchaseDetails'> {
purchaseDetails: {
data: StrapiEntity<
PurchaseDetailsTransformed & {
localizations: {
data: StrapiEntity<PurchaseDetailsTransformed>[];
};
}
>;
purchaseDetails: PurchaseDetailsTransformed & {
localizations: PurchaseDetailsTransformed[];
};
}
export interface PurchaseWithDetailsOfferingContentByPlanIdsResult {
purchases: {
data: StrapiEntity<PurchaseWithDetailsOfferingContentResult>[];
};
purchases: PurchaseWithDetailsOfferingContentResult[];
}

Просмотреть файл

@ -5,42 +5,34 @@ import {
PurchaseDetailsResultFactory,
PurchaseWithDetailsOfferingContentByPlanIdsResultFactory,
} from './factories';
import { PurchaseWithDetailsOfferingContentByPlanIdsResult } from './types';
import { PurchaseWithDetailsOfferingContentUtil } from './util';
describe('PurchaseWithDetailsOfferingContentUtil', () => {
it('should create a util from response', () => {
const result = PurchaseWithDetailsOfferingContentByPlanIdsResultFactory();
const result2 = PurchaseWithDetailsOfferingContentByPlanIdsResultFactory();
const purchase = result.purchases?.data[0];
const planId = purchase.attributes.stripePlanChoices?.[0];
const legacyPlanId =
purchase.attributes.offering.data.attributes.stripeLegacyPlans?.[0];
const util = new PurchaseWithDetailsOfferingContentUtil([
result as PurchaseWithDetailsOfferingContentByPlanIdsResult,
result2 as PurchaseWithDetailsOfferingContentByPlanIdsResult,
]);
const purchase = result.purchases[0];
const planId = purchase.stripePlanChoices?.[0];
const legacyPlanId = purchase.offering.stripeLegacyPlans?.[0];
const util = new PurchaseWithDetailsOfferingContentUtil(result);
expect(util).toBeDefined();
expect(
util.transformedPurchaseWithCommonContentForPlanId(
planId.stripePlanChoice ?? ''
)?.offering.data.attributes.stripeProductId
)?.offering.stripeProductId
).toBeDefined();
expect(
util.transformedPurchaseWithCommonContentForPlanId(
legacyPlanId.stripeLegacyPlan ?? ''
)?.offering.data.attributes.stripeProductId
)?.offering.stripeProductId
).toBeDefined();
expect(util.purchases.data.length).toBe(2);
expect(util.purchases.length).toBe(1);
});
describe('transformPurchaseDetails', () => {
let util: PurchaseWithDetailsOfferingContentUtil;
beforeAll(() => {
const result = PurchaseWithDetailsOfferingContentByPlanIdsResultFactory();
util = new PurchaseWithDetailsOfferingContentUtil([
result as PurchaseWithDetailsOfferingContentByPlanIdsResult,
]);
util = new PurchaseWithDetailsOfferingContentUtil(result);
});
it('should transform details', () => {

Просмотреть файл

@ -15,61 +15,31 @@ export class PurchaseWithDetailsOfferingContentUtil {
> = {};
constructor(
private rawResults: PurchaseWithDetailsOfferingContentByPlanIdsResult[]
private rawResult: PurchaseWithDetailsOfferingContentByPlanIdsResult
) {
for (const rawResult of rawResults) {
for (const purchase of rawResult.purchases.data) {
purchase.attributes.stripePlanChoices?.forEach(
({ stripePlanChoice }) => {
this.transformedPurchaseByPlanId[stripePlanChoice] = {
...purchase.attributes,
purchaseDetails: {
data: {
attributes: {
...this.purchaseDetailsTransform(
purchase.attributes.purchaseDetails.data.attributes
),
localizations: {
data: purchase.attributes.purchaseDetails.data.attributes.localizations.data.map(
(localization) => ({
attributes: this.purchaseDetailsTransform(
localization.attributes
),
})
),
},
},
},
},
};
}
);
purchase.attributes.offering.data.attributes.stripeLegacyPlans?.forEach(
({ stripeLegacyPlan }) => {
this.transformedPurchaseByPlanId[stripeLegacyPlan] = {
...purchase.attributes,
purchaseDetails: {
data: {
attributes: {
...this.purchaseDetailsTransform(
purchase.attributes.purchaseDetails.data.attributes
),
localizations: {
data: purchase.attributes.purchaseDetails.data.attributes.localizations.data.map(
(localization) => ({
attributes: this.purchaseDetailsTransform(
localization.attributes
),
})
),
},
},
},
},
};
}
);
}
for (const purchase of rawResult.purchases) {
purchase.stripePlanChoices?.forEach(({ stripePlanChoice }) => {
this.transformedPurchaseByPlanId[stripePlanChoice] = {
...purchase,
purchaseDetails: {
...this.purchaseDetailsTransform(purchase.purchaseDetails),
localizations: purchase.purchaseDetails.localizations.map(
(localization) => this.purchaseDetailsTransform(localization)
),
},
};
});
purchase.offering.stripeLegacyPlans?.forEach(({ stripeLegacyPlan }) => {
this.transformedPurchaseByPlanId[stripeLegacyPlan] = {
...purchase,
purchaseDetails: {
...this.purchaseDetailsTransform(purchase.purchaseDetails),
localizations: purchase.purchaseDetails.localizations.map(
(localization) => this.purchaseDetailsTransform(localization)
),
},
};
});
}
}
@ -93,17 +63,6 @@ export class PurchaseWithDetailsOfferingContentUtil {
}
get purchases(): PurchaseWithDetailsOfferingContentByPlanIdsResult['purchases'] {
// Deduplicating items as there could be duplicates from splitting up the
// stripePlanIds and making multiple CMS calls
return {
data: [
...new Map(
this.rawResults
.map((rawResult) => rawResult.purchases.data)
.flat()
.map((res) => [JSON.stringify(res), res])
).values(),
],
};
return this.rawResult.purchases;
}
}

Просмотреть файл

@ -6,14 +6,11 @@ import { faker } from '@faker-js/faker';
import { ServicesWithCapabilitiesQuery } from '../../../__generated__/graphql';
import { CapabilitiesResult, ServiceResult } from '.';
import { StrapiEntityFactory } from '../../factories';
export const ServicesWithCapabilitiesQueryFactory = (
override?: Partial<ServicesWithCapabilitiesQuery>
): ServicesWithCapabilitiesQuery => ({
services: {
data: [StrapiEntityFactory(ServiceResultFactory())],
},
services: [ServiceResultFactory()],
...override,
});
@ -21,9 +18,7 @@ export const ServiceResultFactory = (
override?: Partial<ServiceResult>
): ServiceResult => ({
oauthClientId: faker.string.sample(),
capabilities: {
data: [StrapiEntityFactory(CapabilitiesResultFactory())],
},
capabilities: [CapabilitiesResultFactory()],
...override,
});

Просмотреть файл

@ -5,19 +5,11 @@
import { graphql } from '../../../__generated__/gql';
export const servicesWithCapabilitiesQuery = graphql(`
query ServicesWithCapabilities($skip: Int!, $limit: Int!) {
services(pagination: { start: $skip, limit: $limit }) {
data {
attributes {
oauthClientId
capabilities {
data {
attributes {
slug
}
}
}
}
query ServicesWithCapabilities {
services(pagination: { limit: 500 }) {
oauthClientId
capabilities {
slug
}
}
}

Просмотреть файл

@ -2,21 +2,15 @@
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
import { StrapiEntity } from '../../types';
export interface CapabilitiesResult {
slug: string;
}
export interface ServiceResult {
oauthClientId: string;
capabilities: {
data: StrapiEntity<CapabilitiesResult>[];
};
capabilities: CapabilitiesResult[];
}
export interface ServicesWithCapabilitiesResult {
services: {
data: StrapiEntity<ServiceResult>[];
};
services: ServiceResult[];
}

Просмотреть файл

@ -15,7 +15,7 @@ describe('ServicesWithCapabilitiesResultUtil', () => {
result as ServicesWithCapabilitiesResult
);
expect(util).toBeDefined();
expect(util.services.data.length).toBe(1);
expect(util.services.length).toBe(1);
});
it('getServices - should return services and capabilities', () => {
@ -25,12 +25,11 @@ describe('ServicesWithCapabilitiesResultUtil', () => {
);
expect(util.getServices()[0].oauthClientId).toBeDefined();
expect(util.getServices()[0].oauthClientId).toEqual(
result.services?.data[0]?.attributes?.oauthClientId
result.services?.[0]?.oauthClientId
);
expect(util.getServices()[0].capabilities.data).toBeDefined();
expect(util.getServices()[0].capabilities.data[0].attributes.slug).toEqual(
result.services?.data[0]?.attributes?.capabilities?.data[0].attributes
?.slug
expect(util.getServices()[0].capabilities).toBeDefined();
expect(util.getServices()[0].capabilities[0].slug).toEqual(
result.services?.[0]?.capabilities?.[0]?.slug
);
});
});

Просмотреть файл

@ -8,8 +8,9 @@ export class ServicesWithCapabilitiesResultUtil {
constructor(private rawResult: ServicesWithCapabilitiesResult) {}
getServices(): ServiceResult[] {
return this.services.data.map((el) => el.attributes);
return this.services;
}
get services() {
return this.rawResult.services;
}

Просмотреть файл

@ -132,12 +132,7 @@ describe('StrapiClient', () => {
describe('getLocale', () => {
const ACCEPT_LANGUAGE = 'en-US,fr-FR;q=0.7,de-DE;q=0.3';
const localesQueryResult = LocalesResultFactory({
i18NLocales: {
data: [
{ attributes: { code: 'en' } },
{ attributes: { code: 'fr-FR' } },
],
},
i18NLocales: [{ code: 'en' }, { code: 'fr-FR' }],
});
beforeEach(() => {

Просмотреть файл

@ -144,10 +144,7 @@ export class StrapiClient {
private async getLocales(): Promise<string[]> {
const localesResult = (await this.query(localesQuery, {})) as LocalesResult;
return (
localesResult.i18NLocales.data.map((locale) => locale.attributes.code) ||
[]
);
return localesResult.i18NLocales.map((locale) => locale.code) || [];
}
private setupCacheBust() {

Просмотреть файл

@ -17,7 +17,3 @@ export type ContentfulErrorResponse = {
requestId: string;
details?: NonNullable<unknown>;
};
export interface StrapiEntity<T> {
attributes: T;
}

Просмотреть файл

@ -3427,8 +3427,8 @@ describe('#integration - StripeHelper', () => {
transformedPurchaseWithCommonContentForPlanId: (planId) => {
const mockValue =
PurchaseWithDetailsOfferingContentTransformedFactory();
mockValue.purchaseDetails.data.attributes.webIcon = newWebIconURL;
mockValue.purchaseDetails.data.attributes.localizations.data = [];
mockValue.purchaseDetails.webIcon = newWebIconURL;
mockValue.purchaseDetails.localizations = [];
return mockValue;
},
};