fossbook 0.0.7 → 0.0.8
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/README.md +67 -0
- package/lib/mod/config.js +4 -0
- package/lib/mod/page.js +6 -3
- package/lib/posts.js +4 -0
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -86,6 +86,18 @@ module.exports = {
|
|
|
86
86
|
image: "https://example.com/default-image.png",
|
|
87
87
|
theme: "archie",
|
|
88
88
|
|
|
89
|
+
// Optional: URL prefix for posts. Defaults to "posts" -> /posts/<slug>/.
|
|
90
|
+
// Set to "" to serve posts at the site root, /<slug>/.
|
|
91
|
+
postsPath: "posts",
|
|
92
|
+
|
|
93
|
+
// Optional comments (see "Comments" below)
|
|
94
|
+
comments: {
|
|
95
|
+
provider: "utterances",
|
|
96
|
+
repo: "you/your-blog",
|
|
97
|
+
issueTerm: "pathname",
|
|
98
|
+
theme: "github-light",
|
|
99
|
+
},
|
|
100
|
+
|
|
89
101
|
// Directory overrides (defaults shown)
|
|
90
102
|
content: "./content",
|
|
91
103
|
postsDir: "./content/posts",
|
|
@@ -120,6 +132,21 @@ content/posts/My Post Title/
|
|
|
120
132
|
└── feature.png
|
|
121
133
|
```
|
|
122
134
|
|
|
135
|
+
### Post URLs
|
|
136
|
+
|
|
137
|
+
By default, posts are served under `/posts/`, e.g. `/posts/my-post-title/`. To
|
|
138
|
+
change the prefix or move posts to the site root, set `postsPath` in
|
|
139
|
+
`fossbook.config.js`:
|
|
140
|
+
|
|
141
|
+
```js
|
|
142
|
+
postsPath: "", // serves the post above at /my-post-title/ (site root)
|
|
143
|
+
// postsPath: "blog", // or use a different prefix: /blog/my-post-title/
|
|
144
|
+
```
|
|
145
|
+
|
|
146
|
+
This affects the generated output directory, the post URL, post links on the
|
|
147
|
+
home/all-posts/tag pages, and image paths. The on-disk source layout under
|
|
148
|
+
`content/posts/` does not change.
|
|
149
|
+
|
|
123
150
|
## CLI Reference
|
|
124
151
|
|
|
125
152
|
```
|
|
@@ -149,6 +176,46 @@ Fossbook ships with the Archie theme by default. To use a custom theme:
|
|
|
149
176
|
|
|
150
177
|
Theme resolution order: user project `themes/` → built-in `themes/`.
|
|
151
178
|
|
|
179
|
+
## Comments
|
|
180
|
+
|
|
181
|
+
Fossbook supports [utterances](https://utteranc.es) — a commenting widget that
|
|
182
|
+
stores comments as GitHub issues. When enabled, a comment box is rendered at the
|
|
183
|
+
bottom of every post page.
|
|
184
|
+
|
|
185
|
+
### Setup
|
|
186
|
+
|
|
187
|
+
1. Make the repository that backs the comments **public**.
|
|
188
|
+
2. Install the [utterances GitHub App](https://github.com/apps/utterances) on
|
|
189
|
+
that repository so the bot can create issues.
|
|
190
|
+
3. Add a `comments` block to `fossbook.config.js`:
|
|
191
|
+
|
|
192
|
+
```js
|
|
193
|
+
comments: {
|
|
194
|
+
provider: "utterances", // currently the only supported provider
|
|
195
|
+
repo: "you/your-blog", // owner/repo that stores the comment issues
|
|
196
|
+
issueTerm: "pathname", // how a post maps to an issue (see below)
|
|
197
|
+
theme: "github-light", // any utterances theme, e.g. "github-dark"
|
|
198
|
+
},
|
|
199
|
+
```
|
|
200
|
+
|
|
201
|
+
Omit the `comments` block (or set it to `null`) to disable comments.
|
|
202
|
+
|
|
203
|
+
### Options
|
|
204
|
+
|
|
205
|
+
| Field | Required | Default | Description |
|
|
206
|
+
| ----------- | -------- | ---------------- | ---------------------------------------------------------------- |
|
|
207
|
+
| `provider` | yes | — | Must be `"utterances"`. |
|
|
208
|
+
| `repo` | yes | — | `owner/repo` whose issues store the comments. |
|
|
209
|
+
| `issueTerm` | no | `"pathname"` | Mapping between a page and its issue: `pathname`, `url`, `title`, `og:title`. |
|
|
210
|
+
| `theme` | no | `"github-light"` | Any [utterances theme](https://utteranc.es/#configuration). |
|
|
211
|
+
|
|
212
|
+
### Mapping notes
|
|
213
|
+
|
|
214
|
+
With `issueTerm: "pathname"`, each post is matched to a GitHub issue whose title
|
|
215
|
+
equals the page's pathname (with the leading slash stripped). If you change a
|
|
216
|
+
post's URL, the existing comment thread no longer matches — rename the issue
|
|
217
|
+
title to the new pathname to keep the old comments.
|
|
218
|
+
|
|
152
219
|
### Required layout files
|
|
153
220
|
|
|
154
221
|
```
|
package/lib/mod/config.js
CHANGED
|
@@ -17,6 +17,7 @@ const defaults = {
|
|
|
17
17
|
image: "",
|
|
18
18
|
theme: "archie",
|
|
19
19
|
basePath: "", // auto-detected for GitHub Pages project sites, e.g. "/repo-name/"
|
|
20
|
+
postsPath: "posts", // URL prefix for posts: "posts" serves articles at /posts/<slug>/; set "" for root
|
|
20
21
|
comments: null, // { provider: "utterances", repo: "user/repo", issueTerm: "pathname", theme: "github-light" }
|
|
21
22
|
content: "./content",
|
|
22
23
|
postsDir: "./content/posts",
|
|
@@ -91,6 +92,9 @@ function loadConfig(configPath) {
|
|
|
91
92
|
merged.basePath += "/";
|
|
92
93
|
}
|
|
93
94
|
|
|
95
|
+
// Normalize postsPath into a bare segment without surrounding slashes
|
|
96
|
+
merged.postsPath = (merged.postsPath || "").replace(/^\/+|\/+$/g, "");
|
|
97
|
+
|
|
94
98
|
return merged;
|
|
95
99
|
}
|
|
96
100
|
|
package/lib/mod/page.js
CHANGED
|
@@ -26,6 +26,9 @@ module.exports = class Page extends PageBase {
|
|
|
26
26
|
// If there's no .md extension, just get the last part of the path
|
|
27
27
|
this.path = path.basename(filePath);
|
|
28
28
|
}
|
|
29
|
+
// The source folder name, used to locate the post's images on disk.
|
|
30
|
+
// this.path may later be prefixed (e.g. "posts/<slug>") for output/URLs.
|
|
31
|
+
this.slug = this.path;
|
|
29
32
|
// parsed content by fields and body
|
|
30
33
|
const content = fm(mdContent);
|
|
31
34
|
|
|
@@ -75,7 +78,7 @@ module.exports = class Page extends PageBase {
|
|
|
75
78
|
recursive: true,
|
|
76
79
|
});
|
|
77
80
|
|
|
78
|
-
fs.mkdirSync(outPath);
|
|
81
|
+
fs.mkdirSync(outPath, { recursive: true });
|
|
79
82
|
} else {
|
|
80
83
|
// remove the outputPath file if it exists
|
|
81
84
|
const outPath = path.join(this.config.dev.outdir, this.path);
|
|
@@ -96,7 +99,7 @@ module.exports = class Page extends PageBase {
|
|
|
96
99
|
);
|
|
97
100
|
|
|
98
101
|
// if there is the images folder in the output directory.
|
|
99
|
-
const srcImagesDir = path.join(this.config.dev.postsdir, this.
|
|
102
|
+
const srcImagesDir = path.join(this.config.dev.postsdir, this.slug, "images");
|
|
100
103
|
if (
|
|
101
104
|
fs.existsSync(srcImagesDir) &&
|
|
102
105
|
this.path !== ""
|
|
@@ -104,7 +107,7 @@ module.exports = class Page extends PageBase {
|
|
|
104
107
|
// Copy images folder from postsdir to outdir
|
|
105
108
|
const destImagesDir = path.join(this.config.dev.outdir, this.path, "images");
|
|
106
109
|
if (!fs.existsSync(destImagesDir))
|
|
107
|
-
fs.mkdirSync(destImagesDir);
|
|
110
|
+
fs.mkdirSync(destImagesDir, { recursive: true });
|
|
108
111
|
|
|
109
112
|
fs.readdirSync(srcImagesDir).forEach(
|
|
110
113
|
(image) => {
|
package/lib/posts.js
CHANGED
|
@@ -23,6 +23,10 @@ module.exports = class Posts {
|
|
|
23
23
|
}
|
|
24
24
|
const post = new Page(this.config);
|
|
25
25
|
post.readSource(path.join(this.config.dev.postsdir, postPath));
|
|
26
|
+
// Optionally nest posts under a URL prefix (e.g. "posts" -> /posts/<slug>/).
|
|
27
|
+
// post.slug stays the source folder name so image lookups remain correct.
|
|
28
|
+
const prefix = this.config.postsPath ? `${this.config.postsPath}/` : "";
|
|
29
|
+
post.path = `${prefix}${post.slug}`;
|
|
26
30
|
post.url = `${this.config.blogsite}/${post.path}/`;
|
|
27
31
|
post.imageURL = `${this.config.blogsite}/${post.path}/images/${post.image}`;
|
|
28
32
|
this.posts.push(post);
|