Skip to content

Instantly share code, notes, and snippets.

@dtothefp
Created January 11, 2019 16:50
Show Gist options
  • Save dtothefp/4b2a2dada1561a081dac9affde9ecf1b to your computer and use it in GitHub Desktop.
Save dtothefp/4b2a2dada1561a081dac9affde9ecf1b to your computer and use it in GitHub Desktop.
/* eslint-disable */
const { intersection } = require(`lodash`);
const { createClient } = require(`contentful`);
const {
createClient: cmaCreateClient,
} = require(`contentful-management`);
(async () => {
const SPACE_ID = `q5lwz1whkyct`;
const {
CONTENTFUL_ACCESS_TOKEN,
CONTENTFUL_PREVIEW_TOKEN,
CONTENTFUL_ENVIRONMENT = `staging`,
CONTENTFUL_CMA_TOKEN,
// PREVIEW,
include,
} = process.env;
const opts = {
space: SPACE_ID,
environment: CONTENTFUL_ENVIRONMENT,
};
const cmaClient = cmaCreateClient({
accessToken: CONTENTFUL_CMA_TOKEN,
environment_id: CONTENTFUL_ENVIRONMENT,
});
const e = await cmaClient.getSpace(SPACE_ID)
.then((space) => space.getEnvironment(`staging`))
.then((space) => space.getEntry(`1VMEToWrdmKaGqeWUSeM2q`))
debugger;
const prodClient = createClient({
...opts,
accessToken: CONTENTFUL_ACCESS_TOKEN,
});
const previewClient = createClient({
...opts,
accessToken: CONTENTFUL_PREVIEW_TOKEN,
host: `preview.contentful.com`,
});
const reqOpts = {
content_type: `productPage`, // eslint-disable-line camelcase
include: isNaN(include) ? 10 : Number(include),
};
const cmaData = await cmaClient.getSpace(SPACE_ID)
.then((space) => space.getEntries());
const updatedEntryReq = cmaData.items.reduce((list, {sys}) => {
const {publishedVersion, version, id} = sys;
if (version > publishedVersion) {
list.push(
id
// previewClient.getEntry(id)
);
}
return list;
}, []);
const updatedEntries = await Promise.all(updatedEntryReq);
const sortedData = await prodClient.getEntries({
'sys.id': `1RPEMD3g3O8eaM0uYKEGae`,
include: 10,
// order: `-sys.updatedAt`,
});
debugger;
// const previewData = await previewClient.getEntries({
// 'sys.contentType.sys.id[nin]': `productPage,landingPage`,
// order: `-sys.updatedAt`,
// });
const prodPageData = await prodClient.getEntries(reqOpts);
const previewPageData = await previewClient.getEntries(reqOpts);
debugger;
// servicesBarService: D7AFnqoomcgKmOeiU2E4Q
// servicesBar product pages:
// en-GB King size Variant Page
// en-US Wave Mattress Page
// en-CA Wave Mattress Page
// en-US Platform Bed PDP - Furniture
// fr-CA Wave Mattress Page
const recurse = (data, acc = {}) => {
for (const item of data) {
const {sys, fields} = item;
if (!sys) break;
const {id, updatedAt, contentType} = sys;
const contentTypeName = contentType.sys.id;
if (!acc[id]) {
if (!/(productPage|landingPage)/.test(contentTypeName)) {
acc[id] = {
updatedAt,
contentType: contentTypeName,
};
}
const keys = Object.keys(fields);
keys.forEach((key) => {
const fieldData = fields[key];
if (Array.isArray(fieldData)) {
recurse(fieldData, acc);
}
});
}
}
return acc;
};
// Questions:
// 1) webhook for staging for both landingPage and productPage because
// otherwise we need to make a request for both and check for all changed
// 2) includes.Entry vs. items, is there a better way to flatten and sort
// TODO:
// - for single page staging preview only sort data for the payload
// contentType and the linked items associated with the current slug
// - account for different slug structure of landing page
// - autopublish all linked modules for publish
// - how to deal with race conditions between staging and prod "publish" webhooks
const previewDict = recurse(previewPageData.items);
const prodDict = recurse(prodPageData.items);
const getDataToUpdate = async ({preview, current}) => {
const slugs = [];
const modules = [];
for (const id of Object.keys(preview)) {
const previewData = preview[id];
const currentData = current[id];
// TODO: auto publish for draft assuming that is the state
// if current data is undefined
if (currentData) {
const isAfter =
(new Date(previewData.updatedAt) -
new Date(currentData.updatedAt)) > 0;
if (isAfter) {
console.log(`***IS AFTER***`, isAfter);
const d = await previewClient.getEntries({
links_to_entry: id, // eslint-disable-line camelcase
"sys.contentType.sys.id[in]": `productPage,landingPage`,
});
d.items.forEach(({fields}) => {
const {slug} = fields;
if (!slugs.includes(slug)) {
slugs.push(slug);
}
});
modules.push(previewData);
}
}
}
return {slugs, modules};
};
const d = await getDataToUpdate({
preview: previewDict,
current: prodDict,
});
const updatedIntersection = intersection(d.modules, updatedEntries);
debugger;
// createdAt: '2018-11-14T13:48:33.718Z',
// updatedAt: '2018-11-17T00:38:58.186Z',
// createdAt: '2018-11-14T13:48:33.718Z',
// updatedAt: '2018-11-20T00:38:28.163Z',
// try {
// const {items, includes} = await client.getEntries(reqOpts);
// const query = [];
// for (const item of items) {
// const {fields} = item;
// const {slug, modules} = fields;
// if (slug === `/landing-page-playground-dfp-test`) {
// for (const module of modules) {
// const {fields, sys} = module;
// const {identifierName} = fields;
// if (identifierName === `Casper vs. landing page hero`) {
// const {id} = sys;
// query.push(id);
// // const data = await client.getEntry(id);
// // console.log(data);
// }
// }
// }
// }
// const data = await client.getEntries({
// ...reqOpts,
// "sys.id": query[0],
// });
// console.log('data', data);
// } catch (err) {
// // without logging the error response important data from
// // Contentful gets obfuscated
// console.error(err.response); // eslint-disable-line no-console
// throw err;
// }
})();
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment