@jungvonmatt/cssg-plugin-hugo 1.0.5 → 1.3.0
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/CHANGELOG.md +41 -0
- package/index.js +165 -2
- package/package.json +3 -3
package/CHANGELOG.md
CHANGED
|
@@ -3,6 +3,47 @@
|
|
|
3
3
|
All notable changes to this project will be documented in this file.
|
|
4
4
|
See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
|
|
5
5
|
|
|
6
|
+
# [1.3.0](https://github.com/jungvonmatt/contentful-ssg/compare/v1.2.0...v1.3.0) (2022-01-10)
|
|
7
|
+
|
|
8
|
+
|
|
9
|
+
### Features
|
|
10
|
+
|
|
11
|
+
* 🎸 Consider menu reference in page node when building menu ([42499a4](https://github.com/jungvonmatt/contentful-ssg/commit/42499a4efb2f25275d8ea4fb74f72461aa441ba0))
|
|
12
|
+
|
|
13
|
+
|
|
14
|
+
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
# [1.2.0](https://github.com/jungvonmatt/contentful-ssg/compare/v1.1.1...v1.2.0) (2021-12-21)
|
|
18
|
+
|
|
19
|
+
|
|
20
|
+
### Features
|
|
21
|
+
|
|
22
|
+
* 🎸 Generates hugo's menu.toml ([27e95a3](https://github.com/jungvonmatt/contentful-ssg/commit/27e95a33452b1aa5158ee89070889383cee4b6c5))
|
|
23
|
+
|
|
24
|
+
|
|
25
|
+
|
|
26
|
+
|
|
27
|
+
|
|
28
|
+
# [1.1.0](https://github.com/jungvonmatt/contentful-ssg/compare/v1.0.6...v1.1.0) (2021-12-02)
|
|
29
|
+
|
|
30
|
+
|
|
31
|
+
### Bug Fixes
|
|
32
|
+
|
|
33
|
+
* 🐛 Adds <rootDir>/data to managed directories ([d67de2b](https://github.com/jungvonmatt/contentful-ssg/commit/d67de2b4a78771076e5fd1d4e7beec0c1fb65a7d))
|
|
34
|
+
|
|
35
|
+
|
|
36
|
+
|
|
37
|
+
|
|
38
|
+
|
|
39
|
+
## [1.0.6](https://github.com/jungvonmatt/contentful-ssg/compare/v1.0.5...v1.0.6) (2021-12-02)
|
|
40
|
+
|
|
41
|
+
**Note:** Version bump only for package @jungvonmatt/cssg-plugin-hugo
|
|
42
|
+
|
|
43
|
+
|
|
44
|
+
|
|
45
|
+
|
|
46
|
+
|
|
6
47
|
## [1.0.5](https://github.com/jungvonmatt/contentful-ssg/compare/v1.0.4...v1.0.5) (2021-11-30)
|
|
7
48
|
|
|
8
49
|
**Note:** Version bump only for package @jungvonmatt/cssg-plugin-hugo
|
package/index.js
CHANGED
|
@@ -20,9 +20,16 @@ const defaultOptions = {
|
|
|
20
20
|
translationStrategy: STRATEGY_DIRECTORY,
|
|
21
21
|
typeIdI18n: 'd-i18n',
|
|
22
22
|
languageConfig: true,
|
|
23
|
+
menuDepth: 0,
|
|
24
|
+
autoSubMenu: false,
|
|
25
|
+
typeIdMenu: 'c-menu',
|
|
23
26
|
fieldIdHome: 'home',
|
|
24
27
|
fieldIdSlug: 'slug',
|
|
25
28
|
fieldIdParent: 'parent_page',
|
|
29
|
+
fieldIdMenu: 'menu',
|
|
30
|
+
fieldIdMenuEntries: 'entries',
|
|
31
|
+
fieldIdMenuHide: 'hide_in_menu',
|
|
32
|
+
fieldIdMenuPos: 'menu_pos',
|
|
26
33
|
typeConfig: {
|
|
27
34
|
[TYPE_CONTENT]: ['page'],
|
|
28
35
|
},
|
|
@@ -61,7 +68,143 @@ export default (args) => {
|
|
|
61
68
|
return type;
|
|
62
69
|
};
|
|
63
70
|
|
|
71
|
+
const buildMenu = async (transformContext, depth = 0) => {
|
|
72
|
+
const { entry, entryMap } = transformContext;
|
|
73
|
+
const entries = entry.fields?.[options.fieldIdMenuEntries] ?? [];
|
|
74
|
+
const nodes = entries
|
|
75
|
+
.filter((node) => node?.sys?.id && node?.sys?.contentType?.sys?.id)
|
|
76
|
+
.map((node, index) => ({
|
|
77
|
+
identifier: node.sys.id,
|
|
78
|
+
weight: (index + 1) * -10,
|
|
79
|
+
params: {
|
|
80
|
+
id: node.sys.id,
|
|
81
|
+
// eslint-disable-next-line camelcase
|
|
82
|
+
content_type: node.sys.contentType.sys.id,
|
|
83
|
+
},
|
|
84
|
+
}));
|
|
85
|
+
|
|
86
|
+
// Resolve page entry
|
|
87
|
+
const resolvePageEntry = async (entry) => {
|
|
88
|
+
const id = entry?.sys?.id ?? 0;
|
|
89
|
+
const node = entryMap.get(id);
|
|
90
|
+
const contentType = node?.sys?.contentType?.sys?.id ?? '';
|
|
91
|
+
const pageId = node?.fields?.link_to_entry?.sys?.id;
|
|
92
|
+
if (contentType === 'page') {
|
|
93
|
+
return node;
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
if (pageId) {
|
|
97
|
+
return entryMap.get(pageId);
|
|
98
|
+
}
|
|
99
|
+
|
|
100
|
+
if (typeof options.resolvePage === 'function') {
|
|
101
|
+
return options.resolvePage(entry, entryMap);
|
|
102
|
+
}
|
|
103
|
+
};
|
|
104
|
+
|
|
105
|
+
const getChildnodesManual = async (entry, depth, ids = []) => {
|
|
106
|
+
const id = entry?.sys?.id ?? 0;
|
|
107
|
+
const page = await resolvePageEntry(entry);
|
|
108
|
+
const contentType = page?.sys?.contentType?.sys?.id ?? '';
|
|
109
|
+
const menuId = page?.fields?.[options.fieldIdMenu]?.sys?.id;
|
|
110
|
+
|
|
111
|
+
if (
|
|
112
|
+
!id ||
|
|
113
|
+
!contentType ||
|
|
114
|
+
!menuId ||
|
|
115
|
+
!entryMap.has(menuId) ||
|
|
116
|
+
ids.includes(id) ||
|
|
117
|
+
depth <= 0
|
|
118
|
+
) {
|
|
119
|
+
return [];
|
|
120
|
+
}
|
|
121
|
+
|
|
122
|
+
const menu = entryMap.get(menuId);
|
|
123
|
+
const subentries = menu?.fields?.[options.fieldIdMenuEntries] ?? [];
|
|
124
|
+
|
|
125
|
+
const collected = await Promise.all(
|
|
126
|
+
subentries.flatMap((node) => getChildnodesManual(node, depth - 1, [...ids, id]))
|
|
127
|
+
);
|
|
128
|
+
|
|
129
|
+
return [
|
|
130
|
+
...subentries
|
|
131
|
+
.filter((node) => node?.sys?.id && node?.sys?.contentType?.sys?.id)
|
|
132
|
+
.map((node, index) => ({
|
|
133
|
+
identifier: node.sys.id,
|
|
134
|
+
parent: id,
|
|
135
|
+
weight: (index + 1) * -10,
|
|
136
|
+
params: {
|
|
137
|
+
id: node.sys.id,
|
|
138
|
+
// eslint-disable-next-line camelcase
|
|
139
|
+
content_type: node.sys.contentType.sys.id,
|
|
140
|
+
},
|
|
141
|
+
})),
|
|
142
|
+
...collected,
|
|
143
|
+
];
|
|
144
|
+
};
|
|
145
|
+
|
|
146
|
+
const getChildnodesRecursive = async (entry, depth) => {
|
|
147
|
+
const id = entry?.sys?.id ?? 0;
|
|
148
|
+
const page = await resolvePageEntry(id);
|
|
149
|
+
const contentType = page?.sys?.contentType?.sys?.id ?? '';
|
|
150
|
+
|
|
151
|
+
if (!id || !contentType || depth <= 0) {
|
|
152
|
+
return [];
|
|
153
|
+
}
|
|
154
|
+
|
|
155
|
+
const childnodes = [...entryMap.values()].filter(
|
|
156
|
+
(entry) => (entry?.fields?.[options.fieldIdParent]?.sys?.id ?? '') === id
|
|
157
|
+
);
|
|
158
|
+
|
|
159
|
+
// Filter childnodes based on hide_in_menu field
|
|
160
|
+
const filtered = childnodes.filter(
|
|
161
|
+
(entry) => !(entry?.fields?.[options.fieldIdMenuHide] ?? false)
|
|
162
|
+
);
|
|
163
|
+
|
|
164
|
+
// Sort based on menuPos field
|
|
165
|
+
const sorted = [...filtered].sort(
|
|
166
|
+
(a, b) =>
|
|
167
|
+
(a?.fields?.[options.fieldIdMenuPos] ?? Number.MAX_SAFE_INTEGER) -
|
|
168
|
+
(b?.fields?.[options.fieldIdMenuPos] ?? Number.MAX_SAFE_INTEGER)
|
|
169
|
+
);
|
|
170
|
+
|
|
171
|
+
return Array.from(
|
|
172
|
+
await Promise.allSettled([
|
|
173
|
+
...sorted
|
|
174
|
+
.filter((node) => node?.sys?.id && node?.sys?.contentType?.sys?.id)
|
|
175
|
+
.map((node, index) => ({
|
|
176
|
+
identifier: node.sys.id,
|
|
177
|
+
parent: id,
|
|
178
|
+
weight: (index + 1) * -10,
|
|
179
|
+
params: {
|
|
180
|
+
id: node.sys.id,
|
|
181
|
+
// eslint-disable-next-line camelcase
|
|
182
|
+
content_type: node.sys.contentType.sys.id,
|
|
183
|
+
},
|
|
184
|
+
})),
|
|
185
|
+
...sorted.flatMap((node) => getChildnodesRecursive(node, depth - 1)),
|
|
186
|
+
])
|
|
187
|
+
)
|
|
188
|
+
.map((a) => a.value)
|
|
189
|
+
.filter((v) => v);
|
|
190
|
+
};
|
|
191
|
+
|
|
192
|
+
// When autoSubMenu parameter is set, we collect child pages automatically
|
|
193
|
+
// Otherwise we look for dedicated menu entries in page nodes
|
|
194
|
+
const childentries = options.autoSubMenu
|
|
195
|
+
? await Promise.all(entries.flatMap((node) => getChildnodesRecursive(node, depth)))
|
|
196
|
+
: await Promise.all(entries.flatMap((node) => getChildnodesManual(node, depth)));
|
|
197
|
+
|
|
198
|
+
return [...nodes, ...childentries].flat(Infinity).filter((v) => v);
|
|
199
|
+
};
|
|
200
|
+
|
|
64
201
|
return {
|
|
202
|
+
config(prev) {
|
|
203
|
+
const { managedDirectories } = prev || {};
|
|
204
|
+
|
|
205
|
+
return { ...prev, managedDirectories: [...(managedDirectories || []), 'data'] };
|
|
206
|
+
},
|
|
207
|
+
|
|
65
208
|
// Before hook
|
|
66
209
|
async before(runtimeContext) {
|
|
67
210
|
const { helper, converter, data, localized } = runtimeContext;
|
|
@@ -119,8 +262,9 @@ export default (args) => {
|
|
|
119
262
|
);
|
|
120
263
|
|
|
121
264
|
const i18n = Object.fromEntries(locales.map((locale) => [locale.code, {}]));
|
|
265
|
+
const menus = Object.fromEntries(locales.map((locale) => [locale.code, {}]));
|
|
122
266
|
|
|
123
|
-
return { ...runtimeContext, helper, localized: enhancedLocalized, i18n };
|
|
267
|
+
return { ...runtimeContext, helper, localized: enhancedLocalized, i18n, menus };
|
|
124
268
|
},
|
|
125
269
|
|
|
126
270
|
/**
|
|
@@ -225,7 +369,7 @@ export default (args) => {
|
|
|
225
369
|
},
|
|
226
370
|
|
|
227
371
|
async transform(transformContext, runtimeContext) {
|
|
228
|
-
const { content, id, contentTypeId, locale } = transformContext;
|
|
372
|
+
const { content, id, contentTypeId, locale, entry } = transformContext;
|
|
229
373
|
|
|
230
374
|
const type = getEntryType(transformContext);
|
|
231
375
|
|
|
@@ -241,6 +385,15 @@ export default (args) => {
|
|
|
241
385
|
return undefined;
|
|
242
386
|
}
|
|
243
387
|
|
|
388
|
+
// Automatically build hugo menus
|
|
389
|
+
// See https://gohugo.io/content-management/menus/
|
|
390
|
+
if (options.typeIdMenu && contentTypeId === options.typeIdMenu) {
|
|
391
|
+
const { name = 'main' } = entry.fields;
|
|
392
|
+
const menu = await buildMenu(transformContext, options.menuDepth);
|
|
393
|
+
|
|
394
|
+
runtimeContext.menus[locale.code][name] = menu;
|
|
395
|
+
}
|
|
396
|
+
|
|
244
397
|
if (type === TYPE_CONTENT) {
|
|
245
398
|
return {
|
|
246
399
|
...snakeCaseKeys({
|
|
@@ -268,6 +421,16 @@ export default (args) => {
|
|
|
268
421
|
return outputFile(dictionaryPath, toml.stringify({ ...oldContent, ...translations }));
|
|
269
422
|
})
|
|
270
423
|
);
|
|
424
|
+
|
|
425
|
+
const { stringify } = await import('@jungvonmatt/contentful-ssg/converter/toml');
|
|
426
|
+
const menus = runtimeContext?.menus ?? {};
|
|
427
|
+
await Promise.all(
|
|
428
|
+
Object.entries(menus).map(([localeCode, menuData]) => {
|
|
429
|
+
const file = `config/_default/menus.${localeCode}.toml`;
|
|
430
|
+
const data = stringify(menuData);
|
|
431
|
+
return outputFile(file, data);
|
|
432
|
+
})
|
|
433
|
+
);
|
|
271
434
|
},
|
|
272
435
|
};
|
|
273
436
|
};
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@jungvonmatt/cssg-plugin-hugo",
|
|
3
|
-
"version": "1.0
|
|
3
|
+
"version": "1.3.0",
|
|
4
4
|
"description": "",
|
|
5
5
|
"main": "index.js",
|
|
6
6
|
"typings": "./index.d.ts",
|
|
@@ -26,10 +26,10 @@
|
|
|
26
26
|
},
|
|
27
27
|
"homepage": "https://github.com/jungvonmatt/contentful-ssg#readme",
|
|
28
28
|
"dependencies": {
|
|
29
|
-
"@jungvonmatt/contentful-ssg": "^1.0
|
|
29
|
+
"@jungvonmatt/contentful-ssg": "^1.1.0",
|
|
30
30
|
"fs-extra": "^10.0.0",
|
|
31
31
|
"merge-options": "^3.0.4",
|
|
32
32
|
"micromatch": "^4.0.4"
|
|
33
33
|
},
|
|
34
|
-
"gitHead": "
|
|
34
|
+
"gitHead": "2cfe041c72ed9a583e5e45e0fad165772ff37a79"
|
|
35
35
|
}
|