hdoc-tools 0.64.0 → 0.66.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/hdoc-toc.js CHANGED
@@ -118,12 +118,17 @@ class TocModel {
118
118
  }
119
119
 
120
120
  // Resolve a leaf link (path without extension) to a source-relative file.
121
+ // Links may carry a leading slash (both "/docId/page" and "docId/page"
122
+ // appear in real books) — the returned rel is normalized to the
123
+ // slash-free, forward-slash form list_files() produces, or the linked
124
+ // flags and file labels built from it never match.
121
125
  _resolve_file(link) {
122
- const rel = `${link}.md`;
126
+ const clean = String(link).replace(/^\/+/, "");
127
+ const rel = `${clean}.md`;
123
128
  if (fs.existsSync(path.join(this.source_path, rel))) {
124
129
  return { file: rel, fileExists: true };
125
130
  }
126
- const rel_index = path.join(link, "index.md");
131
+ const rel_index = `${clean}/index.md`;
127
132
  if (fs.existsSync(path.join(this.source_path, rel_index))) {
128
133
  return { file: rel_index, fileExists: true };
129
134
  }
@@ -258,8 +263,13 @@ class TocModel {
258
263
  if (segs.includes("..") || segs.includes(".")) {
259
264
  throw new Error("Invalid path");
260
265
  }
261
- if (segs.some((s) => s.startsWith("_"))) {
262
- throw new Error("Cannot operate inside special (_) folders");
266
+ // Special "_" folders are off-limits, with one exception: _inline
267
+ // directly under the book root holds real, editable inline-help pages
268
+ // (they render in serve/build and are exempt from the nav tree).
269
+ for (let i = 0; i < segs.length; i++) {
270
+ if (segs[i].startsWith("_") && !(i === 1 && segs[i] === "_inline")) {
271
+ throw new Error("Cannot operate inside special (_) folders");
272
+ }
263
273
  }
264
274
  if (!dir && exts) {
265
275
  const lower = norm.toLowerCase();
@@ -288,32 +298,43 @@ class TocModel {
288
298
  return set;
289
299
  }
290
300
 
291
- // Every file on disk under the book (excluding "_" folders), each tagged with
301
+ // Every file on disk under the book (excluding "_" folders, except _inline
302
+ // at the book root — those are real inline-help pages), each tagged with
292
303
  // its kind (page/image/other). Pages also carry a linked flag (in nav or not).
293
304
  list_files() {
294
305
  const linked = this.linked_files();
295
306
  const root = path.join(this.source_path, this.docId);
296
307
  const files = [];
297
308
  const dirs = [];
298
- const walk = (absDir) => {
309
+ const walk = (absDir, in_inline) => {
299
310
  for (const e of fs.readdirSync(absDir, { withFileTypes: true })) {
300
- if (e.name.startsWith("_")) continue; // skip special folders/files
311
+ if (e.name.startsWith("_")) {
312
+ // _inline at the book root is editable content; every other
313
+ // _ entry stays hidden (and blocked by _safe_rel)
314
+ if (!(absDir === root && e.name === "_inline" && e.isDirectory()))
315
+ continue;
316
+ }
301
317
  const abs = path.join(absDir, e.name);
302
318
  const rel = path.relative(this.source_path, abs).split(path.sep).join("/");
319
+ const inline = in_inline || e.name === "_inline";
303
320
  if (e.isDirectory()) {
304
321
  dirs.push(rel);
305
- walk(abs);
322
+ walk(abs, inline);
306
323
  } else {
307
324
  const kind = kind_of(e.name);
308
325
  files.push({
309
326
  file: rel,
310
327
  kind,
311
- linked: kind === "page" ? linked.has(rel) : false,
328
+ // _inline pages are referenced from app help contexts, never
329
+ // the contents tree — report them linked so the unlinked
330
+ // badge/filter stays meaningful
331
+ linked:
332
+ kind === "page" ? (inline ? true : linked.has(rel)) : false,
312
333
  });
313
334
  }
314
335
  }
315
336
  };
316
- if (fs.existsSync(root)) walk(root);
337
+ if (fs.existsSync(root)) walk(root, false);
317
338
  files.sort((a, b) => a.file.localeCompare(b.file));
318
339
  dirs.sort((a, b) => a.localeCompare(b));
319
340
  return { docId: this.docId, dirs, files };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "hdoc-tools",
3
- "version": "0.64.0",
3
+ "version": "0.66.0",
4
4
  "description": "Hornbill HDocBook Development Support Tool",
5
5
  "main": "hdoc.js",
6
6
  "bin": {
@@ -23,6 +23,7 @@
23
23
  "hdoc-mermaid.js",
24
24
  "hdoc-module.js",
25
25
  "hdoc-serve.js",
26
+ "hdoc-serve-validate.js",
26
27
  "hdoc-spell.js",
27
28
  "hdoc-stats.js",
28
29
  "hdoc-toc.js",
package/ui/index.html CHANGED
@@ -413,7 +413,9 @@
413
413
  <i v-bind:class="{'bi bi-chevron-right': !asection.expand,'bi bi-chevron-down': asection.expand}" class="bi"></i>
414
414
  </div>
415
415
  </div>
416
- <span class="title-text">{{asection.text}}</span>
416
+ <!-- LOCAL PREVIEW PATCH: draft/inline badges so authors can see unpublished
417
+ sections in `hdoc serve`/`hdoc edit` - keep on live-site re-sync -->
418
+ <span class="title-text"><i v-if="asection.draft" class="bi bi-exclamation-triangle-fill text-danger" title="This section is set to draft."></i><i v-if="asection.inline" class="bi bi-files-alt text-warning" title="This section is set to inline."></i> {{asection.text}}</span>
417
419
  </div>
418
420
  <!-- A collapsed group now renders NOTHING instead of hidden DOM. With v-show, every
419
421
  descendant of every collapsed group stayed in the document: on a large book that
@@ -429,7 +431,8 @@
429
431
 
430
432
  <div v-if="!navSectionItem.items">
431
433
  <a class="DocLink link noitems" v-bind:href="navSectionItem.link" v-bind:target="navSectionItem.target || ''" style="padding-left: 0px;">
432
- <span class="link-text">{{navSectionItem.text}} <i v-if="navSectionItem.target" class="bi bi-box-arrow-up-right"></i> </span>
434
+ <!-- LOCAL PREVIEW PATCH: draft badge on leaf links - keep on live-site re-sync -->
435
+ <span class="link-text"><i v-if="navSectionItem.draft" class="bi bi-exclamation-triangle-fill text-danger" title="This page is set to draft."></i> {{navSectionItem.text}} <i v-if="navSectionItem.target" class="bi bi-box-arrow-up-right"></i> </span>
433
436
  </a>
434
437
  </div>
435
438
 
@@ -82,7 +82,8 @@ function loadJS(arrFiles,callback)
82
82
  "js/doc.hornbill.js",
83
83
  "js/highlightjs/highlight.pack.js",
84
84
  "js/highlightjs-badge.js",
85
- "js/hdoc-edit-inline.js" //-- LOCAL PREVIEW PATCH: inline edit for `hdoc serve` (no-op unless the server enables it) - keep on live-site re-sync
85
+ "js/hdoc-edit-inline.js", //-- LOCAL PREVIEW PATCH: inline edit for `hdoc serve` (no-op unless the server enables it) - keep on live-site re-sync
86
+ "js/hdoc-edit-book.js" //-- LOCAL PREVIEW PATCH: Edit Mode suite (contents/files management) for `hdoc serve` - keep on live-site re-sync
86
87
  ],function()
87
88
  {
88
89
  intialiseApp();
@@ -839,7 +839,21 @@ var docAppMethods = {
839
839
  view.docApp.book = data;
840
840
  view.docApp.title = data.title || "";
841
841
  view.docApp.description = data.description || "";
842
-
842
+
843
+ //-- LOCAL PREVIEW PATCH: `hdoc serve`/`hdoc edit` publish the book's _inline/
844
+ //-- content as a nav_inline fragment on the library.json book entry (see
845
+ //-- hdoc-content-routes.js build_nav_inline). Append it to the nav tree so
846
+ //-- inline help pages are reachable from the menu - keep on live-site re-sync.
847
+ //-- look the book up in the library rather than trusting aBook: some call
848
+ //-- sites (e.g. search result clicks) pass a bare {docId} stub.
849
+ var libBook = getLibraryBooksIndex().get(data.docId) || aBook;
850
+ var navInline = libBook && libBook.nav_inline;
851
+ if(navInline && Array.isArray(navInline.items) && navInline.items.length &&
852
+ data.navigation && Array.isArray(data.navigation.items))
853
+ {
854
+ data.navigation.items.push(navInline);
855
+ }
856
+
843
857
 
844
858
  view.docApp.loadingBookInfo = false; //-- move this here into timeout to avoid loading glitch that shows main landing page
845
859