@nascentdigital/funnel-cms 5.0.1 → 5.0.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/contentful/ContentfulAccess.d.ts +19 -0
- package/dist/contentful/ContentfulAccess.js +67 -0
- package/dist/contentful/ContentfulApiCommand.d.ts +21 -0
- package/dist/contentful/ContentfulApiCommand.js +20 -0
- package/dist/contentful/ContentfulApiResponse.d.ts +10 -0
- package/dist/contentful/ContentfulApiResponse.js +2 -0
- package/dist/contentful/ContentfulAssetClient.d.ts +11 -0
- package/dist/contentful/ContentfulAssetClient.js +26 -0
- package/dist/contentful/ContentfulAuthClient.d.ts +9 -0
- package/dist/contentful/ContentfulAuthClient.js +20 -0
- package/dist/contentful/ContentfulChangeSetClient.d.ts +14 -0
- package/dist/contentful/ContentfulChangeSetClient.js +35 -0
- package/dist/contentful/ContentfulCollectionClient.d.ts +38 -0
- package/dist/contentful/ContentfulCollectionClient.js +173 -0
- package/dist/contentful/ContentfulContentClient.d.ts +60 -0
- package/dist/contentful/ContentfulContentClient.js +272 -0
- package/dist/contentful/ContentfulContentClientFactory.d.ts +12 -0
- package/dist/contentful/ContentfulContentClientFactory.js +19 -0
- package/dist/contentful/ContentfulPageClient.d.ts +43 -0
- package/dist/contentful/ContentfulPageClient.js +459 -0
- package/dist/contentful/ContentfulSiteConfigClient.d.ts +9 -0
- package/dist/contentful/ContentfulSiteConfigClient.js +33 -0
- package/dist/contentful/ContentfulUpgradeClient.d.ts +9 -0
- package/dist/contentful/ContentfulUpgradeClient.js +17 -0
- package/dist/contentful/ContentfulUserClient.d.ts +13 -0
- package/dist/contentful/ContentfulUserClient.js +32 -0
- package/dist/contentful/IContentfulContentClient.d.ts +61 -0
- package/dist/contentful/IContentfulContentClient.js +2 -0
- package/dist/contentful/api/ContentfulApi.d.ts +10 -0
- package/dist/contentful/api/ContentfulApi.js +82 -0
- package/dist/contentful/index.d.ts +12 -0
- package/dist/contentful/index.js +28 -0
- package/dist/contentful/models/ContentfulAssetData.d.ts +10 -0
- package/dist/contentful/models/ContentfulAssetData.js +29 -0
- package/dist/contentful/models/ContentfulCollectionData.d.ts +13 -0
- package/dist/contentful/models/ContentfulCollectionData.js +98 -0
- package/dist/contentful/models/ContentfulData.d.ts +39 -0
- package/dist/contentful/models/ContentfulData.js +118 -0
- package/dist/contentful/models/ContentfulPageData.d.ts +19 -0
- package/dist/contentful/models/ContentfulPageData.js +117 -0
- package/dist/contentful/models/ContentfulSiteConfigData.d.ts +10 -0
- package/dist/contentful/models/ContentfulSiteConfigData.js +9 -0
- package/dist/contentful/models/ContentfulUserData.d.ts +6 -0
- package/dist/contentful/models/ContentfulUserData.js +26 -0
- package/dist/contentful/models/index.d.ts +6 -0
- package/dist/contentful/models/index.js +22 -0
- package/dist/contentful/server.d.ts +1 -0
- package/dist/contentful/server.js +17 -0
- package/dist/models/Pagination.d.ts +1 -0
- package/dist/strapi/StrapiPageClient.js +11 -10
- package/package.json +9 -3
|
@@ -0,0 +1,459 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __rest = (this && this.__rest) || function (s, e) {
|
|
3
|
+
var t = {};
|
|
4
|
+
for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0)
|
|
5
|
+
t[p] = s[p];
|
|
6
|
+
if (s != null && typeof Object.getOwnPropertySymbols === "function")
|
|
7
|
+
for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) {
|
|
8
|
+
if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i]))
|
|
9
|
+
t[p[i]] = s[p[i]];
|
|
10
|
+
}
|
|
11
|
+
return t;
|
|
12
|
+
};
|
|
13
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
14
|
+
exports.ContentfulPageClient = void 0;
|
|
15
|
+
const funnel_core_1 = require("@nascentdigital/funnel-core");
|
|
16
|
+
const errors_1 = require("../errors");
|
|
17
|
+
const models_1 = require("./models");
|
|
18
|
+
// class
|
|
19
|
+
class ContentfulPageClient {
|
|
20
|
+
constructor(cms) {
|
|
21
|
+
this.cms = cms;
|
|
22
|
+
}
|
|
23
|
+
async getOverview(args) {
|
|
24
|
+
// fetch all pages
|
|
25
|
+
const { cms } = this;
|
|
26
|
+
const { entries } = await cms.getEntries(Object.assign({ content_type: models_1.ContentfulPageData.contentType, version: args.version, select: getPageSelect(funnel_core_1.Schema.Page.Data.AsLink.props) }, getPageQueryParams(args)));
|
|
27
|
+
// convert entries to page data
|
|
28
|
+
const pagesData = entries.map(entry => models_1.ContentfulPageData.deserialize(entry, funnel_core_1.Schema.Page.Data.AsLink.props));
|
|
29
|
+
// setup maps
|
|
30
|
+
const staticPages = new Map();
|
|
31
|
+
const dynamicPages = new Map();
|
|
32
|
+
// go over each page data
|
|
33
|
+
for (const data of pagesData) {
|
|
34
|
+
// use appropriate map (determine if page is static/dynamic)
|
|
35
|
+
const pagesMap = data.slug === undefined
|
|
36
|
+
? staticPages
|
|
37
|
+
: dynamicPages;
|
|
38
|
+
// get references by page type
|
|
39
|
+
let refs = pagesMap.get(data.type);
|
|
40
|
+
if (!refs) {
|
|
41
|
+
pagesMap.set(data.type, refs = []);
|
|
42
|
+
}
|
|
43
|
+
// add to refs
|
|
44
|
+
refs.push(data);
|
|
45
|
+
}
|
|
46
|
+
// return
|
|
47
|
+
return {
|
|
48
|
+
// static pages
|
|
49
|
+
static: staticPages.entries().map(([type, refs]) => ({
|
|
50
|
+
type,
|
|
51
|
+
refs: refs.reduce((refs, ref) => {
|
|
52
|
+
// add page
|
|
53
|
+
refs[ref.language] = ref;
|
|
54
|
+
// keep reducing
|
|
55
|
+
return refs;
|
|
56
|
+
}, {})
|
|
57
|
+
})).toArray(),
|
|
58
|
+
// dynamic pages
|
|
59
|
+
dynamic: dynamicPages.entries().map(([type, refs]) => ({
|
|
60
|
+
type,
|
|
61
|
+
count: refs.length
|
|
62
|
+
})).toArray()
|
|
63
|
+
};
|
|
64
|
+
}
|
|
65
|
+
async getSummaries(args) {
|
|
66
|
+
// fetch items (bail if there are no instances)
|
|
67
|
+
const { cms } = this;
|
|
68
|
+
const { entries } = await cms.getEntries(Object.assign({ content_type: models_1.ContentfulPageData.contentType, version: args.version, select: getPageSelect(funnel_core_1.Schema.Page.Data.AsLink.props) }, getPageQueryParams(args)));
|
|
69
|
+
// return result
|
|
70
|
+
return entries.map(entry => models_1.ContentfulPageData.deserialize(entry, funnel_core_1.Schema.Page.Data.AsLink.props));
|
|
71
|
+
}
|
|
72
|
+
getPreviews(args) {
|
|
73
|
+
throw new funnel_core_1.NotImplementedError();
|
|
74
|
+
}
|
|
75
|
+
async search(args) {
|
|
76
|
+
// fetch items (bail if there are no instances)
|
|
77
|
+
const { cms } = this;
|
|
78
|
+
const { entries, page, pageCount, totalItemCount } = await cms.getEntries(Object.assign({ content_type: models_1.ContentfulPageData.contentType, version: args.version, select: getPageSelect(funnel_core_1.Schema.Page.Data.AsLink.props) }, getPageQueryParams(args)));
|
|
79
|
+
// return entries
|
|
80
|
+
return {
|
|
81
|
+
items: entries.map(entry => models_1.ContentfulPageData.deserialize(entry, funnel_core_1.Schema.Page.Data.AsLink.props)),
|
|
82
|
+
page, pageCount, totalItemCount
|
|
83
|
+
};
|
|
84
|
+
}
|
|
85
|
+
query(args) {
|
|
86
|
+
throw new funnel_core_1.NotImplementedError();
|
|
87
|
+
}
|
|
88
|
+
find(args) {
|
|
89
|
+
throw new funnel_core_1.NotImplementedError();
|
|
90
|
+
}
|
|
91
|
+
async getGroup(args) {
|
|
92
|
+
// fetch items (bail if there are no instances
|
|
93
|
+
const { language, region, version } = args, queryArgs = __rest(args, ["language", "region", "version"]);
|
|
94
|
+
const { cms } = this;
|
|
95
|
+
const { entries } = await cms.getEntries(Object.assign({ content_type: models_1.ContentfulPageData.contentType, version, select: getPageSelect(funnel_core_1.Schema.Page.Data.AsGroup.Instance.props) }, getPageQueryParams(queryArgs)));
|
|
96
|
+
// bail if no items
|
|
97
|
+
if (entries.length === 0) {
|
|
98
|
+
console.debug('[ContentfulPageClient/getGroup] no items in group', args);
|
|
99
|
+
const { brand, groupId: possibleGroupId, type, slug } = queryArgs;
|
|
100
|
+
return {
|
|
101
|
+
group: { groupId: possibleGroupId !== null && possibleGroupId !== void 0 ? possibleGroupId : funnel_core_1.Schema.Page.GroupId.empty, brand, type, slug, instances: [] }
|
|
102
|
+
};
|
|
103
|
+
}
|
|
104
|
+
console.debug('[ContentfulPageClient/getGroup] processing group items', args);
|
|
105
|
+
// collate the group ids into summaries (fetches full page if region/language match exists
|
|
106
|
+
const instances = entries.map(entry => models_1.ContentfulPageData.deserialize(entry, funnel_core_1.Schema.Page.Data.AsGroup.Instance.props));
|
|
107
|
+
// bind page (if it exists)
|
|
108
|
+
const pageInstance = instances
|
|
109
|
+
.find(instance => instance.region === region && instance.language === language);
|
|
110
|
+
console.debug('[ContentfulPageClient/getGroup] getting page using this.get...', { id: pageInstance === null || pageInstance === void 0 ? void 0 : pageInstance.id, version });
|
|
111
|
+
const page = pageInstance
|
|
112
|
+
? await this.get({ id: pageInstance.id, version })
|
|
113
|
+
: undefined;
|
|
114
|
+
// return group (and optional page)
|
|
115
|
+
const { type, brand, groupId, slug } = entries[0];
|
|
116
|
+
return {
|
|
117
|
+
group: { groupId, type, brand, slug, instances },
|
|
118
|
+
page
|
|
119
|
+
};
|
|
120
|
+
}
|
|
121
|
+
async get(args) {
|
|
122
|
+
// create args for query
|
|
123
|
+
const queryArgs = 'id' in args
|
|
124
|
+
? { ids: [args.id], version: args.version }
|
|
125
|
+
: args;
|
|
126
|
+
// fetch entries (should be one entry)
|
|
127
|
+
const { cms } = this;
|
|
128
|
+
const { entries, references } = await cms.getEntries(Object.assign({ content_type: models_1.ContentfulPageData.contentType, includeLinks: true, version: args.version, pagination: { page: 1, pageSize: 1 } }, getPageQueryParams(queryArgs)));
|
|
129
|
+
// skip if no entries
|
|
130
|
+
if (entries.length === 0) {
|
|
131
|
+
return undefined;
|
|
132
|
+
}
|
|
133
|
+
// use first entry and deserialize
|
|
134
|
+
return Object.assign({ data: models_1.ContentfulPageData.deserialize(entries[0]) }, models_1.ContentfulPageData.deserializeRefs(references));
|
|
135
|
+
}
|
|
136
|
+
async create(args) {
|
|
137
|
+
console.debug('[ContentfulPageClient/create] processing create page request', args);
|
|
138
|
+
// create a new language of an existing page
|
|
139
|
+
if (funnel_core_1.Schema.Page.Data.AsNewLanguage.filter(args)) {
|
|
140
|
+
// fetch all pages in group (summaries only)
|
|
141
|
+
const existingPages = await this.getSummaries({
|
|
142
|
+
version: 'draft',
|
|
143
|
+
brand: args.brand,
|
|
144
|
+
groupId: args.groupId
|
|
145
|
+
});
|
|
146
|
+
// throw if there are no pages
|
|
147
|
+
if (existingPages.length === 0) {
|
|
148
|
+
throw new funnel_core_1.ArgumentError(`Page group "${args.groupId}" no longer exists in "${args.brand}"`);
|
|
149
|
+
}
|
|
150
|
+
// return existing page if it's there
|
|
151
|
+
let existingPage = existingPages
|
|
152
|
+
.find(existing => existing.region === args.region && existing.language === args.language);
|
|
153
|
+
if (existingPage) {
|
|
154
|
+
console.debug('[ContentfulPageClient/create/lang] returning existing page', existingPage);
|
|
155
|
+
return this.getGroup(Object.assign(Object.assign({}, existingPage), { version: 'draft' }));
|
|
156
|
+
}
|
|
157
|
+
// bind data + update url
|
|
158
|
+
existingPage = existingPages[0];
|
|
159
|
+
const draft = funnel_core_1.Schema.PageModel.fromDraft(Object.assign({ type: existingPage.type, slug: existingPage.slug, url: existingPage.url, name: existingPage.name, tags: existingPage.tags }, args));
|
|
160
|
+
draft.sync();
|
|
161
|
+
console.debug('[ContentfulPageClient/create/lang] creating from', { draft, existingPages });
|
|
162
|
+
// create page
|
|
163
|
+
try {
|
|
164
|
+
// create page
|
|
165
|
+
const draftData = draft.data;
|
|
166
|
+
const references = models_1.ContentfulData.findReferences([draftData.discover, draftData.content]);
|
|
167
|
+
const pageData = await this.cms.createEntry(models_1.ContentfulPageData.contentType, {
|
|
168
|
+
groupId: draftData.groupId,
|
|
169
|
+
brand: draftData.brand,
|
|
170
|
+
type: draftData.type,
|
|
171
|
+
region: draftData.region,
|
|
172
|
+
language: draftData.language,
|
|
173
|
+
name: draftData.name,
|
|
174
|
+
tags: draftData.tags,
|
|
175
|
+
slug: draftData.slug,
|
|
176
|
+
url: draftData.url,
|
|
177
|
+
preview: draftData.preview,
|
|
178
|
+
discover: draftData.discover,
|
|
179
|
+
content: draftData.content,
|
|
180
|
+
state: 'draft',
|
|
181
|
+
errors: true,
|
|
182
|
+
references
|
|
183
|
+
});
|
|
184
|
+
// transform entry to page data
|
|
185
|
+
const flattenedPage = {
|
|
186
|
+
data: pageData,
|
|
187
|
+
files: {},
|
|
188
|
+
collections: {},
|
|
189
|
+
pages: {}
|
|
190
|
+
};
|
|
191
|
+
const page = flattenedPage.data;
|
|
192
|
+
// return new page
|
|
193
|
+
return {
|
|
194
|
+
group: {
|
|
195
|
+
groupId: page.groupId,
|
|
196
|
+
brand: page.brand,
|
|
197
|
+
type: page.type,
|
|
198
|
+
slug: page.slug,
|
|
199
|
+
instances: [
|
|
200
|
+
// map exiting entries
|
|
201
|
+
...existingPages.map(({ id, url, region, language, name, slug, tags, state, errors, createdOn, updatedOn, publishedOn }) => ({ id, url, region, language, name, slug, tags, state, errors, createdOn, updatedOn, publishedOn })),
|
|
202
|
+
// add new entry
|
|
203
|
+
{
|
|
204
|
+
id: page.id,
|
|
205
|
+
url: page.url,
|
|
206
|
+
region: page.region,
|
|
207
|
+
language: page.language,
|
|
208
|
+
name: page.name,
|
|
209
|
+
slug: page.slug,
|
|
210
|
+
tags: page.tags,
|
|
211
|
+
state: page.state,
|
|
212
|
+
errors: page.errors,
|
|
213
|
+
createdOn: page.createdOn,
|
|
214
|
+
updatedOn: page.updatedOn,
|
|
215
|
+
publishedOn: page.publishedOn
|
|
216
|
+
}
|
|
217
|
+
]
|
|
218
|
+
},
|
|
219
|
+
page: flattenedPage
|
|
220
|
+
};
|
|
221
|
+
}
|
|
222
|
+
// or throw
|
|
223
|
+
catch (e) {
|
|
224
|
+
throw funnel_core_1.IsometricErrorUtils.coerceError(e);
|
|
225
|
+
}
|
|
226
|
+
}
|
|
227
|
+
// or create a net-new page
|
|
228
|
+
else {
|
|
229
|
+
console.debug('[ContentfulPageClient/create/new] creating fresh');
|
|
230
|
+
// get page's template
|
|
231
|
+
const site = funnel_core_1.Schema.Site.current();
|
|
232
|
+
const schema = site.regions[args.region][args.type];
|
|
233
|
+
// check slug if dynamic page
|
|
234
|
+
if (schema.variant === 'dynamic') {
|
|
235
|
+
// make sure there is a slug for a dynamic page
|
|
236
|
+
if (args.slug === undefined) {
|
|
237
|
+
throw new funnel_core_1.ArgumentError(`A "${args.type}" Page must provide a slug when created`);
|
|
238
|
+
}
|
|
239
|
+
// validate slug
|
|
240
|
+
const validateSlugResult = await this.validateSlug(Object.assign(Object.assign({}, args), { slug: args.slug }));
|
|
241
|
+
if (validateSlugResult.status !== 'available') {
|
|
242
|
+
throw new errors_1.SlugValidationError({ slug: args.slug, reason: validateSlugResult });
|
|
243
|
+
}
|
|
244
|
+
}
|
|
245
|
+
// fetch all pages matching brand/type/region
|
|
246
|
+
const { group: existingGroup, page: existingPage } = await this.getGroup({
|
|
247
|
+
version: 'draft',
|
|
248
|
+
brand: args.brand,
|
|
249
|
+
type: args.type,
|
|
250
|
+
region: args.region,
|
|
251
|
+
language: args.language,
|
|
252
|
+
slug: args.slug
|
|
253
|
+
});
|
|
254
|
+
// return existing page if it's there
|
|
255
|
+
if (existingPage) {
|
|
256
|
+
console.debug('[ContentfulPageClient/create/new] returning existing page', existingPage);
|
|
257
|
+
return { group: existingGroup, page: existingPage };
|
|
258
|
+
}
|
|
259
|
+
else if (existingGroup.instances.length > 0) {
|
|
260
|
+
console.debug('[ContentfulPageClient/create/new] using existing group', existingGroup);
|
|
261
|
+
}
|
|
262
|
+
else {
|
|
263
|
+
console.debug('[ContentfulPageClient/create/new] no existing group found');
|
|
264
|
+
}
|
|
265
|
+
// bind data + update url
|
|
266
|
+
const draft = funnel_core_1.Schema.PageModel.fromDraft(Object.assign(Object.assign({}, args), { groupId: existingGroup.groupId === funnel_core_1.Schema.Page.GroupId.empty
|
|
267
|
+
? funnel_core_1.Value.uuid()
|
|
268
|
+
: existingGroup.groupId, url: '' }));
|
|
269
|
+
draft.sync();
|
|
270
|
+
// create page
|
|
271
|
+
try {
|
|
272
|
+
console.debug('[ContentfulPageClient/create/new] adding new page', draft.data);
|
|
273
|
+
// create page
|
|
274
|
+
const draftData = draft.data;
|
|
275
|
+
const references = models_1.ContentfulData.findReferences([draftData.discover, draftData.content]);
|
|
276
|
+
const pageData = await this.cms.createEntry(models_1.ContentfulPageData.contentType, {
|
|
277
|
+
groupId: draftData.groupId,
|
|
278
|
+
brand: draftData.brand,
|
|
279
|
+
type: draftData.type,
|
|
280
|
+
region: draftData.region,
|
|
281
|
+
language: draftData.language,
|
|
282
|
+
name: draftData.name,
|
|
283
|
+
tags: draftData.tags,
|
|
284
|
+
slug: draftData.slug,
|
|
285
|
+
url: draftData.url,
|
|
286
|
+
preview: draftData.preview,
|
|
287
|
+
discover: draftData.discover,
|
|
288
|
+
content: draftData.content,
|
|
289
|
+
state: 'draft',
|
|
290
|
+
errors: true,
|
|
291
|
+
references
|
|
292
|
+
});
|
|
293
|
+
// transform entry to page data
|
|
294
|
+
const flattenedPage = {
|
|
295
|
+
data: pageData,
|
|
296
|
+
files: {},
|
|
297
|
+
collections: {},
|
|
298
|
+
pages: {}
|
|
299
|
+
};
|
|
300
|
+
const page = flattenedPage.data;
|
|
301
|
+
// return page
|
|
302
|
+
return {
|
|
303
|
+
group: {
|
|
304
|
+
groupId: page.groupId,
|
|
305
|
+
brand: page.brand,
|
|
306
|
+
type: page.type,
|
|
307
|
+
slug: page.slug,
|
|
308
|
+
instances: [
|
|
309
|
+
...existingGroup.instances,
|
|
310
|
+
{
|
|
311
|
+
id: page.id,
|
|
312
|
+
url: page.url,
|
|
313
|
+
region: page.region,
|
|
314
|
+
language: page.language,
|
|
315
|
+
name: page.name,
|
|
316
|
+
slug: page.slug,
|
|
317
|
+
tags: page.tags,
|
|
318
|
+
state: page.state,
|
|
319
|
+
errors: page.errors,
|
|
320
|
+
createdOn: page.createdOn,
|
|
321
|
+
updatedOn: page.updatedOn,
|
|
322
|
+
publishedOn: page.publishedOn
|
|
323
|
+
}
|
|
324
|
+
]
|
|
325
|
+
},
|
|
326
|
+
page: flattenedPage
|
|
327
|
+
};
|
|
328
|
+
}
|
|
329
|
+
// or throw
|
|
330
|
+
catch (e) {
|
|
331
|
+
throw funnel_core_1.IsometricErrorUtils.coerceError(e);
|
|
332
|
+
}
|
|
333
|
+
}
|
|
334
|
+
}
|
|
335
|
+
duplicate(args) {
|
|
336
|
+
throw new funnel_core_1.NotImplementedError();
|
|
337
|
+
}
|
|
338
|
+
update(args) {
|
|
339
|
+
throw new funnel_core_1.NotImplementedError();
|
|
340
|
+
}
|
|
341
|
+
replace(args) {
|
|
342
|
+
throw new funnel_core_1.NotImplementedError();
|
|
343
|
+
}
|
|
344
|
+
touch(args) {
|
|
345
|
+
throw new funnel_core_1.NotImplementedError();
|
|
346
|
+
}
|
|
347
|
+
unpublish(args) {
|
|
348
|
+
throw new funnel_core_1.NotImplementedError();
|
|
349
|
+
}
|
|
350
|
+
getDependants(args) {
|
|
351
|
+
throw new funnel_core_1.NotImplementedError();
|
|
352
|
+
}
|
|
353
|
+
getDependencies(args) {
|
|
354
|
+
throw new funnel_core_1.NotImplementedError();
|
|
355
|
+
}
|
|
356
|
+
validateSlug(args) {
|
|
357
|
+
throw new funnel_core_1.NotImplementedError();
|
|
358
|
+
}
|
|
359
|
+
}
|
|
360
|
+
exports.ContentfulPageClient = ContentfulPageClient;
|
|
361
|
+
// helpers
|
|
362
|
+
function getPageQueryParams(query) {
|
|
363
|
+
// build filters
|
|
364
|
+
const { ids = [], groupId, brand, type, slug, region, language, name, tags = [], tagsMatch = 'any', version } = query;
|
|
365
|
+
const filters = {};
|
|
366
|
+
// filter id(s)
|
|
367
|
+
if (ids.length === 1) {
|
|
368
|
+
filters['sys.id'] = ids[0];
|
|
369
|
+
}
|
|
370
|
+
else if (ids.length > 1) {
|
|
371
|
+
filters['sys.id[in]'] = ids.join(',');
|
|
372
|
+
}
|
|
373
|
+
// filter group
|
|
374
|
+
if (groupId) {
|
|
375
|
+
filters['fields.groupId'] = groupId;
|
|
376
|
+
}
|
|
377
|
+
// filter brand
|
|
378
|
+
if (brand) {
|
|
379
|
+
filters['fields.brand'] = brand;
|
|
380
|
+
}
|
|
381
|
+
// filter type(s)
|
|
382
|
+
const normalizedType = type
|
|
383
|
+
? Array.isArray(type)
|
|
384
|
+
? type
|
|
385
|
+
: [type]
|
|
386
|
+
: [];
|
|
387
|
+
if (normalizedType.length === 1) {
|
|
388
|
+
filters['fields.type'] = normalizedType[0];
|
|
389
|
+
}
|
|
390
|
+
else if (normalizedType.length > 1) {
|
|
391
|
+
filters['fields.type[in]'] = normalizedType.join(',');
|
|
392
|
+
}
|
|
393
|
+
// filter slug
|
|
394
|
+
if (slug) {
|
|
395
|
+
filters['fields.slug'] = slug;
|
|
396
|
+
}
|
|
397
|
+
// filter region
|
|
398
|
+
if (region) {
|
|
399
|
+
filters['fields.region'] = region;
|
|
400
|
+
}
|
|
401
|
+
// filter language
|
|
402
|
+
if (language) {
|
|
403
|
+
filters['fields.language'] = language;
|
|
404
|
+
}
|
|
405
|
+
// filter name
|
|
406
|
+
if (name) {
|
|
407
|
+
filters['fields.name[match]'] = name;
|
|
408
|
+
}
|
|
409
|
+
// filter tags
|
|
410
|
+
if (tags.length > 0) {
|
|
411
|
+
filters[`fields.tags[${tagsMatch === 'any' ? 'in' : 'all'}]`] = tags
|
|
412
|
+
.filter((tag) => !!tag)
|
|
413
|
+
.join(',');
|
|
414
|
+
}
|
|
415
|
+
// return filters
|
|
416
|
+
return filters;
|
|
417
|
+
}
|
|
418
|
+
function getPageSelect(props) {
|
|
419
|
+
// build select
|
|
420
|
+
const select = new Set(['sys']);
|
|
421
|
+
for (const prop of props) {
|
|
422
|
+
switch (prop) {
|
|
423
|
+
// parity
|
|
424
|
+
case 'groupId':
|
|
425
|
+
case 'brand':
|
|
426
|
+
case 'type':
|
|
427
|
+
case 'slug':
|
|
428
|
+
case 'url':
|
|
429
|
+
case 'region':
|
|
430
|
+
case 'language':
|
|
431
|
+
case 'name':
|
|
432
|
+
case 'tags':
|
|
433
|
+
case 'discover':
|
|
434
|
+
case 'preview':
|
|
435
|
+
case 'content':
|
|
436
|
+
case 'state':
|
|
437
|
+
case 'errors':
|
|
438
|
+
case 'publishedOn':
|
|
439
|
+
case 'publication':
|
|
440
|
+
select.add(`fields.${prop}`);
|
|
441
|
+
break;
|
|
442
|
+
// links
|
|
443
|
+
case 'files':
|
|
444
|
+
case 'pages':
|
|
445
|
+
case 'collections':
|
|
446
|
+
select.add('fields.references');
|
|
447
|
+
break;
|
|
448
|
+
// ignore the rest
|
|
449
|
+
default:
|
|
450
|
+
break;
|
|
451
|
+
}
|
|
452
|
+
}
|
|
453
|
+
// bail if nothing added
|
|
454
|
+
if (select.size === 0) {
|
|
455
|
+
return undefined;
|
|
456
|
+
}
|
|
457
|
+
// return as joint string
|
|
458
|
+
return Array.from(select).join(',');
|
|
459
|
+
}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { SiteConfigClient } from '../api';
|
|
2
|
+
import { IContentfulContentClient } from './IContentfulContentClient';
|
|
3
|
+
import { ContentfulSiteConfigData } from './models';
|
|
4
|
+
export declare class ContentfulSiteConfigClient implements SiteConfigClient {
|
|
5
|
+
readonly cms: IContentfulContentClient;
|
|
6
|
+
constructor(cms: IContentfulContentClient);
|
|
7
|
+
get({ brand }: SiteConfigClient.Get.Args): Promise<ContentfulSiteConfigData>;
|
|
8
|
+
update(args: SiteConfigClient.Update.Args): Promise<SiteConfigClient.Update.Result>;
|
|
9
|
+
}
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.ContentfulSiteConfigClient = void 0;
|
|
4
|
+
const funnel_core_1 = require("@nascentdigital/funnel-core");
|
|
5
|
+
const models_1 = require("./models");
|
|
6
|
+
// class
|
|
7
|
+
class ContentfulSiteConfigClient {
|
|
8
|
+
constructor(cms) {
|
|
9
|
+
this.cms = cms;
|
|
10
|
+
}
|
|
11
|
+
async get({ brand }) {
|
|
12
|
+
// fetch config model
|
|
13
|
+
let { entries: [siteConfig] } = await this.cms.getEntries({
|
|
14
|
+
content_type: models_1.ContentfulSiteConfigData.contentType,
|
|
15
|
+
pagination: { page: 1, pageSize: 1 },
|
|
16
|
+
'fields.brand': brand
|
|
17
|
+
});
|
|
18
|
+
// or create it if it's not there
|
|
19
|
+
if (!siteConfig) {
|
|
20
|
+
siteConfig = await this.cms.createEntry(models_1.ContentfulSiteConfigData.contentType, {
|
|
21
|
+
brand,
|
|
22
|
+
lockdownEditor: false,
|
|
23
|
+
access: {}
|
|
24
|
+
});
|
|
25
|
+
}
|
|
26
|
+
// return config
|
|
27
|
+
return siteConfig;
|
|
28
|
+
}
|
|
29
|
+
update(args) {
|
|
30
|
+
throw new funnel_core_1.NotImplementedError();
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
exports.ContentfulSiteConfigClient = ContentfulSiteConfigClient;
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { UpgradeClient } from '../api';
|
|
2
|
+
import { Upgrade } from '../models';
|
|
3
|
+
import { IContentfulContentClient } from './IContentfulContentClient';
|
|
4
|
+
export declare class ContentfulUpgradeClient implements UpgradeClient {
|
|
5
|
+
readonly cms: IContentfulContentClient;
|
|
6
|
+
constructor(cms: IContentfulContentClient);
|
|
7
|
+
status(): Promise<Upgrade.Status>;
|
|
8
|
+
upgrade(): Promise<Upgrade.Status>;
|
|
9
|
+
}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.ContentfulUpgradeClient = void 0;
|
|
4
|
+
const funnel_core_1 = require("@nascentdigital/funnel-core");
|
|
5
|
+
// class
|
|
6
|
+
class ContentfulUpgradeClient {
|
|
7
|
+
constructor(cms) {
|
|
8
|
+
this.cms = cms;
|
|
9
|
+
}
|
|
10
|
+
status() {
|
|
11
|
+
throw new funnel_core_1.NotImplementedError();
|
|
12
|
+
}
|
|
13
|
+
upgrade() {
|
|
14
|
+
throw new funnel_core_1.NotImplementedError();
|
|
15
|
+
}
|
|
16
|
+
}
|
|
17
|
+
exports.ContentfulUpgradeClient = ContentfulUpgradeClient;
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import { UserClient } from '../api';
|
|
2
|
+
import { IContentfulContentClient } from './IContentfulContentClient';
|
|
3
|
+
export declare class ContentfulUserClient implements UserClient {
|
|
4
|
+
readonly cms: IContentfulContentClient;
|
|
5
|
+
constructor(cms: IContentfulContentClient);
|
|
6
|
+
me(): Promise<UserClient.Me.Result>;
|
|
7
|
+
getUsers(args?: UserClient.GetUsers.Args): Promise<UserClient.GetUsers.Result>;
|
|
8
|
+
getUser(args: UserClient.GetUser.Args): Promise<UserClient.GetUser.Result>;
|
|
9
|
+
createUser(args: UserClient.CreateUser.Args): Promise<UserClient.CreateUser.Result>;
|
|
10
|
+
updateUser(args: UserClient.UpdateUser.Args): Promise<UserClient.UpdateUser.Result>;
|
|
11
|
+
resetUser(args: UserClient.ResetUser.Args): Promise<UserClient.ResetUser.Result>;
|
|
12
|
+
deleteUser(args: UserClient.DeleteUser.Args): Promise<UserClient.DeleteUser.Result>;
|
|
13
|
+
}
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.ContentfulUserClient = void 0;
|
|
4
|
+
const funnel_core_1 = require("@nascentdigital/funnel-core");
|
|
5
|
+
// class
|
|
6
|
+
class ContentfulUserClient {
|
|
7
|
+
constructor(cms) {
|
|
8
|
+
this.cms = cms;
|
|
9
|
+
}
|
|
10
|
+
async me() {
|
|
11
|
+
return this.cms.user.data;
|
|
12
|
+
}
|
|
13
|
+
getUsers(args) {
|
|
14
|
+
throw new funnel_core_1.NotImplementedError();
|
|
15
|
+
}
|
|
16
|
+
getUser(args) {
|
|
17
|
+
throw new funnel_core_1.NotImplementedError();
|
|
18
|
+
}
|
|
19
|
+
createUser(args) {
|
|
20
|
+
throw new funnel_core_1.NotImplementedError();
|
|
21
|
+
}
|
|
22
|
+
updateUser(args) {
|
|
23
|
+
throw new funnel_core_1.NotImplementedError();
|
|
24
|
+
}
|
|
25
|
+
resetUser(args) {
|
|
26
|
+
throw new funnel_core_1.NotImplementedError();
|
|
27
|
+
}
|
|
28
|
+
deleteUser(args) {
|
|
29
|
+
throw new funnel_core_1.NotImplementedError();
|
|
30
|
+
}
|
|
31
|
+
}
|
|
32
|
+
exports.ContentfulUserClient = ContentfulUserClient;
|
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
import { CMAClient } from '@contentful/app-sdk';
|
|
2
|
+
import { PlainClientAPI, QueryOptions } from 'contentful-management';
|
|
3
|
+
import { AssetClient } from '../api';
|
|
4
|
+
import { Environment, Pagination, User } from '../models';
|
|
5
|
+
import type { ContentfulAssetClient } from './ContentfulAssetClient';
|
|
6
|
+
import type { ContentfulAuthClient } from './ContentfulAuthClient';
|
|
7
|
+
import type { ContentfulChangeSetClient } from './ContentfulChangeSetClient';
|
|
8
|
+
import type { ContentfulCollectionClient } from './ContentfulCollectionClient';
|
|
9
|
+
import type { ContentfulPageClient } from './ContentfulPageClient';
|
|
10
|
+
import type { ContentfulSiteConfigClient } from './ContentfulSiteConfigClient';
|
|
11
|
+
import type { ContentfulUserClient } from './ContentfulUserClient';
|
|
12
|
+
import { ContentfulAssetData, ContentfulData } from './models';
|
|
13
|
+
export interface IContentfulContentClient {
|
|
14
|
+
readonly user: User;
|
|
15
|
+
readonly locale: string;
|
|
16
|
+
readonly cma: CMAClient;
|
|
17
|
+
readonly cda: PlainClientAPI;
|
|
18
|
+
readonly cpa: PlainClientAPI;
|
|
19
|
+
readonly auth: ContentfulAuthClient;
|
|
20
|
+
readonly changeSets: ContentfulChangeSetClient;
|
|
21
|
+
readonly files: ContentfulAssetClient;
|
|
22
|
+
readonly pages: ContentfulPageClient;
|
|
23
|
+
readonly collections: ContentfulCollectionClient;
|
|
24
|
+
readonly users: ContentfulUserClient;
|
|
25
|
+
readonly siteConfig: ContentfulSiteConfigClient;
|
|
26
|
+
createEntry<TEntry extends ContentfulData>(contentType: string, entry: ContentfulData.Draft<TEntry>): Promise<TEntry>;
|
|
27
|
+
getEntry<TEntry extends ContentfulData>(args: IContentfulContentClient.GetEntry.Args<TEntry>): Promise<IContentfulContentClient.GetEntry.Result<TEntry>>;
|
|
28
|
+
getEntries<TEntry extends ContentfulData>(args: IContentfulContentClient.GetEntries.Args<TEntry>): Promise<IContentfulContentClient.GetEntries.Result<TEntry>>;
|
|
29
|
+
uploadAsset(args: IContentfulContentClient.UploadAsset.Args): Promise<IContentfulContentClient.UploadAsset.Result>;
|
|
30
|
+
}
|
|
31
|
+
export declare namespace IContentfulContentClient {
|
|
32
|
+
type EntryQueryOptions = {
|
|
33
|
+
includeLinks?: boolean | number;
|
|
34
|
+
version?: Environment;
|
|
35
|
+
};
|
|
36
|
+
namespace GetEntry {
|
|
37
|
+
type Args<TEntry extends ContentfulData> = EntryQueryOptions & {
|
|
38
|
+
entryId: ContentfulData.EntryId<TEntry>;
|
|
39
|
+
};
|
|
40
|
+
type Result<TEntry extends ContentfulData> = {
|
|
41
|
+
entry: TEntry;
|
|
42
|
+
references: ContentfulData[];
|
|
43
|
+
};
|
|
44
|
+
}
|
|
45
|
+
namespace GetEntries {
|
|
46
|
+
type Args<TEntry extends ContentfulData> = Omit<QueryOptions, 'content_type' | 'include' | 'limit' | 'skip'> & EntryQueryOptions & {
|
|
47
|
+
content_type: ContentfulData.ContentType<TEntry>;
|
|
48
|
+
pagination?: Pagination;
|
|
49
|
+
};
|
|
50
|
+
type Result<TEntry extends ContentfulData> = Pagination.Counts & {
|
|
51
|
+
entries: TEntry[];
|
|
52
|
+
references: ContentfulData[];
|
|
53
|
+
};
|
|
54
|
+
}
|
|
55
|
+
namespace UploadAsset {
|
|
56
|
+
type Args = AssetClient.CreateAsset.Args & {
|
|
57
|
+
file: Blob;
|
|
58
|
+
};
|
|
59
|
+
type Result = ContentfulAssetData;
|
|
60
|
+
}
|
|
61
|
+
}
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import 'server-only';
|
|
2
|
+
import type { NextRequest, NextResponse as NextResponseType } from 'next/server';
|
|
3
|
+
import { ContentfulApiCommand } from '../ContentfulApiCommand';
|
|
4
|
+
export declare namespace ContentfulApi {
|
|
5
|
+
function process(request: NextRequest, NextResponse: typeof NextResponseType): Promise<NextResponseType<{
|
|
6
|
+
data: ContentfulApiCommand.GetAccessTokens.Result;
|
|
7
|
+
}> | NextResponseType<{
|
|
8
|
+
error: import("@nascentdigital/funnel-core").SerializedIsometricError;
|
|
9
|
+
}>>;
|
|
10
|
+
}
|