Skip to content

Commit 3181ed4

Browse files
committed
Implement: Homepage can be a folder with assets
- Add few tests for raw html homepage - both root and foldered
1 parent f97bd5a commit 3181ed4

5 files changed

Lines changed: 153 additions & 10 deletions

File tree

src/compiler/contentModel/fsToContent.js

Lines changed: 41 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,12 @@ const Dictionary = require('../../dictionary')
44
const { last } = require('../../helpers')
55
const { createLocalAsset } = require('./models/localAsset')
66
const { createAssets } = require('./models/asset')
7-
const { createHomepage } = require('./models/homepage')
7+
8+
const {
9+
createHomepage,
10+
createFolderedHomepage,
11+
createFolderedHomepageIndex
12+
} = require('./models/homepage')
813

914
const {
1015
createCategory,
@@ -54,6 +59,12 @@ const isHomepageFile = (fsObject) => {
5459
return isTemplateFile(fsObject) && fsObject.name.match(/^(homepage|home|index)\..+$/)
5560
}
5661

62+
const isHomepageDirectory = (fsObject) => {
63+
const { homepageDirectory } = Settings.getSettings()
64+
const pattern = new RegExp(`^(${homepageDirectory}|homepage|home)$`)
65+
return fsObject.name.match(pattern)
66+
}
67+
5768
const newEntry = ({
5869
contentModel,
5970
key,
@@ -126,6 +137,31 @@ const withHomepage = (contentModel, fsObject) => {
126137
})
127138
}
128139

140+
const withFolderedHomepage = (contentModel, fsObject) => {
141+
return newEntry({
142+
contentModel,
143+
key: 'homepage',
144+
entryFn: () => {
145+
const homepage = createFolderedHomepage({
146+
...fsObject,
147+
children: fsObject.children.map(mapFolderedHomepageTree)
148+
})
149+
return homepage.data
150+
},
151+
replace: true
152+
})
153+
}
154+
155+
const mapFolderedHomepageTree = (fsObject) => {
156+
if (isHomepageFile(fsObject)) {
157+
return createFolderedHomepageIndex(fsObject)
158+
}
159+
return createLocalAsset({
160+
...fsObject,
161+
isFolder: !!fsObject.children
162+
})
163+
}
164+
129165
const withSubpages = (contentModel, fsObject) => {
130166
return newEntry({
131167
contentModel,
@@ -276,6 +312,9 @@ const createContentModel = (fsTree) => {
276312
if (!fsObject.children) {
277313
return withLocalAsset(contentModel, fsObject)
278314
}
315+
if (isHomepageDirectory(fsObject)) {
316+
return withFolderedHomepage(contentModel, fsObject)
317+
}
279318
if (fsObject.name === pagesDirectory) {
280319
return withSubpages(contentModel, fsObject)
281320
}
@@ -293,7 +332,7 @@ const createContentModel = (fsTree) => {
293332
subpages: [],
294333
categories: [],
295334
posts: [],
296-
homepage: createHomepage().data,
335+
homepage: createHomepage({}).data,
297336
localAssets: [],
298337
tags: []
299338
})
Lines changed: 42 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,30 +1,65 @@
1+
const _ = require('lodash')
12
const Settings = require('../../../settings')
23
const contentTypes = require('../contentTypes')
34
const parseTemplate = require('../parseTemplate')
5+
const { isLocalAsset } = require('./localAsset')
6+
7+
const isFolderedHomepageIndex = (fsObject) => {
8+
return fsObject.type === contentTypes.FOLDERED_HOMEPAGE_INDEX
9+
}
10+
11+
const _createHomepage = (fsObject, { foldered }) => {
12+
const indexFile = foldered ?
13+
fsObject.children.find(isFolderedHomepageIndex) :
14+
fsObject
15+
16+
const localAssets = foldered ?
17+
fsObject.children.filter(isLocalAsset) :
18+
[]
419

5-
const createHomepage = (fsObject = {}) => {
620
const permalink = Settings.getSettings().permalinkPrefix
721

8-
const metadata = fsObject ?
9-
parseTemplate(fsObject, { permalink }) :
10-
{ attributes: {} }
22+
const metadata = parseTemplate(indexFile, {
23+
permalink,
24+
localAssets
25+
})
1126

12-
const type = fsObject.extension === '.html' ? 'raw-index-html' : 'basic'
27+
const type = indexFile.extension === '.html' ? 'raw-index-html' : 'basic'
1328

1429
return {
15-
...(fsObject || {}),
30+
..._.omit(fsObject, 'children'),
1631
type: contentTypes.HOMEPAGE,
1732
data: {
1833
type: metadata.type || type,
1934
title: metadata.title || '',
2035
content: metadata.content || '',
2136
mentions: metadata.mentions || [],
2237
...metadata.attributes,
38+
foldered,
39+
localAssets,
2340
permalink
2441
}
2542
}
2643
}
2744

45+
const createFolderedHomepageIndex = (fsObject) => {
46+
return {
47+
...fsObject,
48+
type: contentTypes.FOLDERED_HOMEPAGE_INDEX
49+
}
50+
}
51+
52+
const createHomepage = (fsObject) => {
53+
return _createHomepage(fsObject, { foldered: false })
54+
}
55+
56+
const createFolderedHomepage = (fsObject) => {
57+
return _createHomepage(fsObject, { foldered: true })
58+
}
59+
2860
module.exports = {
29-
createHomepage
61+
createHomepage,
62+
createFolderedHomepage,
63+
isFolderedHomepageIndex,
64+
createFolderedHomepageIndex
3065
}

src/compiler/rendering/views/local-assets.js

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,7 @@ const copyAsset = async ({ basePath, destPath, path, name, isFolder }) => {
2828
}
2929
}
3030

31-
const copyLocalAssets = async ({ localAssets, posts, subpages, categories }) => {
31+
const copyLocalAssets = async ({ localAssets, homepage, posts, subpages, categories }) => {
3232
const { rootDirectory, contentDirectory, pagesDirectory } = Settings.getSettings()
3333
const basePath = await contentRoot(rootDirectory, contentDirectory)
3434

@@ -38,6 +38,16 @@ const copyLocalAssets = async ({ localAssets, posts, subpages, categories }) =>
3838
.map(copyAsset)
3939
)
4040

41+
const copyHomepageAssets = all(
42+
(homepage.localAssets || []).map((localAsset) => {
43+
const assetWithBasePath = withBasePath(basePath)(localAsset)
44+
return copyAsset({
45+
...assetWithBasePath,
46+
destPath: '.'
47+
})
48+
})
49+
)
50+
4151
const copyCategoryAssets = all(
4252
categories.map(({ localAssets }) => {
4353
return all(
@@ -74,6 +84,7 @@ const copyLocalAssets = async ({ localAssets, posts, subpages, categories }) =>
7484

7585
return all([
7686
copyRootAssets,
87+
copyHomepageAssets,
7788
copyCategoryAssets,
7889
copyPostAssets,
7990
copySubpageAssets

src/settings.js

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ const defaultSettings = (rootDirectory) => ({
1313
permalinkPrefix: "/",
1414
assetsDirectory: "assets",
1515
exportDirectory: "docs",
16+
homepageDirectory: "homepage",
1617
pagesDirectory: "pages",
1718
themeDirectory: "theme",
1819
contentDirectory: "content",

src/tests/programmatic.js

Lines changed: 57 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -129,6 +129,63 @@ test('post files in a category', async t => {
129129
hasPaths(t, categoryDir, compiledPostNames)
130130
})
131131

132+
test('homepage', async t => {
133+
const { exportDirectory, homepageDirectory } = writ.getDefaultSettings()
134+
135+
const dir = await createTempDir(t)
136+
const rawHTMLHomepageContent = 'raw html homepage'
137+
await dir.mkFile('index.html', rawHTMLHomepageContent)
138+
139+
await writ.build({
140+
rootDirectory: dir.name
141+
})
142+
143+
await common.builds(t, dir.name, {
144+
rootDirectoryPaths: {
145+
exists: ['index.html']
146+
},
147+
exportDirectoryPaths: {
148+
exists: ['index.html']
149+
}
150+
})
151+
152+
const actualRawHTMLOutputContent = await readFile(join(dir.name, exportDirectory, 'index.html'), { encoding: 'utf-8' })
153+
const expectedRawHTMLOutputContent = new RegExp(`^${rawHTMLHomepageContent}$`, 's')
154+
t.match(
155+
actualRawHTMLOutputContent,
156+
expectedRawHTMLOutputContent,
157+
"When homepage file has .html extension, it's treated as raw HTML"
158+
)
159+
160+
await rm(join(dir.name, 'index.html'))
161+
162+
const folderedHomepageContent = 'I am foldered homepage'
163+
await dir.mkDir(homepageDirectory)
164+
await dir.mkFile(join(homepageDirectory, 'index.html'), folderedHomepageContent)
165+
166+
await writ.build({
167+
rootDirectory: dir.name
168+
})
169+
170+
await common.builds(t, dir.name, {
171+
rootDirectoryPaths: {
172+
exists: [homepageDirectory]
173+
},
174+
exportDirectoryPaths: {
175+
notExists: [homepageDirectory],
176+
exists: ['index.html']
177+
}
178+
})
179+
180+
const actualFolderedOutputContent = await readFile(join(dir.name, exportDirectory, 'index.html'), { encoding: 'utf-8' })
181+
const expectedFolderedOutputContent = new RegExp(`^${folderedHomepageContent}$`, 's')
182+
t.match(
183+
actualFolderedOutputContent,
184+
expectedFolderedOutputContent,
185+
'Using a homepage folder works'
186+
)
187+
})
188+
132189
test('subpages', async t => {
133190
const dir = await createTempDir(t)
134191

0 commit comments

Comments
 (0)