-
Notifications
You must be signed in to change notification settings - Fork 0
/
gatsby-node.js
134 lines (118 loc) · 4.4 KB
/
gatsby-node.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
/**
* Implement Gatsby's Node APIs in this file.
*
* See: https://www.gatsbyjs.org/docs/node-apis/
*/
// You can delete this file if you're not using it
const _ = require(`lodash`)
const Promise = require(`bluebird`)
const path = require(`path`)
const slash = require(`slash`)
/**
* Fix problem when fields are empty in CMS but we call the structure of content with Graphql, Gatsby are working on this issue: https://github.com/gatsbyjs/gatsby/issues/3344
* Add default values to node fields that might be empty from CMS
**/
// const { attachFields } = require(`gatsby-plugin-node-fields`)
// // List of descriptors
// const descriptors = [
// {
// predicate: node => node.internal.type === 'ContentfulNavigationItem',
// fields: [
// {
// name: 'url',
// getter: node => node.url,
// defaultValue: null,
// }
// ]
// }
// ]
// exports.onCreateNode = ({ node, actions }) => {
// const { createNodeField } = actions
// attachFields(node, createNodeField, descriptors)
// }
// Extend Contentful pages graphql response to include full page path based on child pages
exports.sourceNodes = ({ getNodes, actions }) => {
const { createNodeField } = actions;
// Get nodes that are pages
const pageNodes = getNodes().filter(
node => node.internal.type === "ContentfulPage"
);
// Loop each page
pageNodes.forEach(pageNode => {
let pathFragments = [];
let tmpNode = pageNode;
// While node has page___NODE (parent page) push the slug to pathFragments array
do {
pathFragments.push(tmpNode.slug);
if (typeof tmpNode.page___NODE === 'object') {
tmpNode = pageNodes.find( node => {
return node.id === tmpNode.page___NODE[0]
});
} else {
tmpNode = false
}
} while (tmpNode);
// Create path by joining all slugs divided with a /
const path = pathFragments.reverse().join("/");
// Add path field to contentful page node accessible through graphql
createNodeField({
node: pageNode,
name: `path`,
value: path
});
});
};
// Implement the Gatsby API “createPages”. This is
// called after the Gatsby bootstrap is finished so you have
// access to any information necessary to programmatically
// create pages.
exports.createPages = ({ graphql, actions }) => {
const { createPage } = actions
return new Promise((resolve, reject) => {
// The “graphql” function allows us to run arbitrary
// queries against the local Contentful graphql schema. Think of
// it like the site has a built-in database constructed
// from the fetched data that you can run queries against.
graphql(
`
{
allContentfulPage {
edges {
node {
id
fields {
path
}
}
}
}
}
`
).then(result => {
if (result.errors) {
reject(result.errors)
}
// Create Category pages
const pageTemplate = path.resolve(`./src/templates/page.js`)
// We want to create a detailed page for each
// category node. We'll just use the Contentful id for the slug.
_.each(result.data.allContentfulPage.edges, edge => {
// Gatsby uses Redux to manage its internal state.
// Plugins and sites can use functions like "createPage"
// to interact with Gatsby.
createPage({
// Each page is required to have a `path` as well
// as a template component. The `context` is
// optional but is often necessary so the template
// can query data specific to each page.
path: `/${edge.node.fields.path}/`,
component: slash(pageTemplate),
context: {
id: edge.node.id,
},
})
})
resolve()
})
})
}