@shadow-garden/bapbong-headless 0.1.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/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 Le Phuoc Minh
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md ADDED
@@ -0,0 +1,56 @@
1
+ # @shadow-garden/bapbong-headless
2
+
3
+ The **backend façade** for bapbong. One install that re-exports the entire
4
+ *isomorphic tier* — no DOM, no canvas, no `prosemirror-view` — so a server can
5
+ read, edit, and write `.docx` with zero browser dependencies.
6
+
7
+ It re-exports:
8
+
9
+ | Package | What you get |
10
+ | --- | --- |
11
+ | `@shadow-garden/bapbong-contracts` | Shared types — `PageConfig`, `Align`, `Command`, `Collection`, … |
12
+ | `@shadow-garden/bapbong-model` | The ProseMirror `schema` (+ `numbering`) |
13
+ | `@shadow-garden/bapbong-docx` | `importDocx` / `exportDocx` round-trip |
14
+ | `@shadow-garden/bapbong-commands` | Headless editor ops — `toggleMarkCommand`, `setAlign`, `insertRow`, `defaultCommands()`, … |
15
+
16
+ ## Install
17
+
18
+ ```sh
19
+ pnpm add @shadow-garden/bapbong-headless prosemirror-state
20
+ ```
21
+
22
+ `prosemirror-state` is a peer of the workflow below — the commands operate on an
23
+ `EditorState`, which you construct yourself (the same one the editor UI uses).
24
+
25
+ ## Backend round-trip
26
+
27
+ ```ts
28
+ import {
29
+ importDocx,
30
+ exportDocx,
31
+ toggleMarkCommand,
32
+ setAlign,
33
+ } from '@shadow-garden/bapbong-headless';
34
+ import { EditorState, TextSelection } from 'prosemirror-state';
35
+
36
+ // 1. Read a .docx (ArrayBuffer | Uint8Array | Blob).
37
+ const imported = await importDocx(bytes);
38
+
39
+ // 2. Drive the SAME commands the editor UI uses, on a Node EditorState.
40
+ let state = EditorState.create({ doc: imported.doc });
41
+ state = state.apply(state.tr.setSelection(TextSelection.create(state.doc, 1, 12)));
42
+ toggleMarkCommand('bold', 'strong').run(state, (tr) => (state = state.apply(tr)));
43
+ setAlign('center').run(state, (tr) => (state = state.apply(tr)));
44
+
45
+ // 3. Write it back. `carry` keeps parts bapbong doesn't model yet (styles,
46
+ // numbering, headers/footers, …) instead of dropping them.
47
+ const out = await exportDocx(state.doc, { carry: imported.raw });
48
+ ```
49
+
50
+ ## Boundary
51
+
52
+ This package is tagged `scope:headless` and lint-guarded against DOM globals
53
+ (`document`, `window`, `Image`, `DOMParser`, …). **Do not** add
54
+ `bapbong-editor` or `bapbong-view` to it — they pull in canvas/DOM and would
55
+ break Node usage. For an in-browser preview use `@shadow-garden/bapbong-view`;
56
+ for a full editor use `@shadow-garden/bapbong-editor`.
package/dist/index.cjs ADDED
@@ -0,0 +1,54 @@
1
+ "use strict";
2
+ var __defProp = Object.defineProperty;
3
+ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
4
+ var __getOwnPropNames = Object.getOwnPropertyNames;
5
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
6
+ var __export = (target, all) => {
7
+ for (var name in all)
8
+ __defProp(target, name, { get: all[name], enumerable: true });
9
+ };
10
+ var __copyProps = (to, from, except, desc) => {
11
+ if (from && typeof from === "object" || typeof from === "function") {
12
+ for (let key of __getOwnPropNames(from))
13
+ if (!__hasOwnProp.call(to, key) && key !== except)
14
+ __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
15
+ }
16
+ return to;
17
+ };
18
+ var __reExport = (target, mod, secondTarget) => (__copyProps(target, mod, "default"), secondTarget && __copyProps(secondTarget, mod, "default"));
19
+ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
20
+
21
+ // packages/headless/src/index.ts
22
+ var index_exports = {};
23
+ __export(index_exports, {
24
+ FontRegistry: () => import_bapbong_measuring.FontRegistry,
25
+ createApproxMeasurer: () => import_bapbong_measuring.createApproxMeasurer,
26
+ createApproxMetrics: () => import_bapbong_measuring.createApproxMetrics,
27
+ createFontRegistryMeasurer: () => import_bapbong_measuring.createFontRegistryMeasurer,
28
+ createFontRegistryMetrics: () => import_bapbong_measuring.createFontRegistryMetrics,
29
+ createLayoutCache: () => import_bapbong_layout_engine.createLayoutCache,
30
+ fontToCss: () => import_bapbong_measuring.fontToCss,
31
+ layout: () => import_bapbong_layout_engine.layout
32
+ });
33
+ module.exports = __toCommonJS(index_exports);
34
+ __reExport(index_exports, require("@shadow-garden/bapbong-contracts"), module.exports);
35
+ __reExport(index_exports, require("@shadow-garden/bapbong-model"), module.exports);
36
+ __reExport(index_exports, require("@shadow-garden/bapbong-docx"), module.exports);
37
+ __reExport(index_exports, require("@shadow-garden/bapbong-commands"), module.exports);
38
+ var import_bapbong_layout_engine = require("@shadow-garden/bapbong-layout-engine");
39
+ var import_bapbong_measuring = require("@shadow-garden/bapbong-measuring");
40
+ // Annotate the CommonJS export names for ESM import in node:
41
+ 0 && (module.exports = {
42
+ FontRegistry,
43
+ createApproxMeasurer,
44
+ createApproxMetrics,
45
+ createFontRegistryMeasurer,
46
+ createFontRegistryMetrics,
47
+ createLayoutCache,
48
+ fontToCss,
49
+ layout,
50
+ ...require("@shadow-garden/bapbong-contracts"),
51
+ ...require("@shadow-garden/bapbong-model"),
52
+ ...require("@shadow-garden/bapbong-docx"),
53
+ ...require("@shadow-garden/bapbong-commands")
54
+ });
@@ -0,0 +1,33 @@
1
+ /**
2
+ * `@shadow-garden/bapbong-headless` — the backend façade.
3
+ *
4
+ * One install that re-exports the whole **isomorphic tier** (no DOM, no canvas):
5
+ * - `bapbong-contracts` — shared types (PageConfig, Align, Command, …)
6
+ * - `bapbong-model` — the ProseMirror `schema` + numbering
7
+ * - `bapbong-docx` — `importDocx` / `exportDocx`
8
+ * - `bapbong-commands` — headless editor ops (toggleMark, setAlign, …)
9
+ *
10
+ * The whole surface runs on Node/server. A backend imports a `.docx`, builds a
11
+ * ProseMirror `EditorState` from the doc, mutates it through the same `commands`
12
+ * the editor UI uses, then exports a `.docx` back — with zero browser deps.
13
+ *
14
+ * import { importDocx, exportDocx, setAlign } from '@shadow-garden/bapbong-headless';
15
+ * import { EditorState } from 'prosemirror-state';
16
+ *
17
+ * Layout/pagination is included too: font-file metrics made it DOM-free, so a
18
+ * backend can paginate (e.g. server-side PDF) with the SAME pure `layout` engine
19
+ * and measurers the editor uses — identical measurer + doc ⇒ identical page
20
+ * breaks (client↔server parity). Only the DOM-free measuring surface is
21
+ * re-exported; the canvas measurers stay out (they need a browser).
22
+ *
23
+ * Do NOT add `bapbong-editor` or `bapbong-view` here — they drag in canvas/DOM
24
+ * and would break Node usage. The `scope:headless` lint boundary enforces this.
25
+ */
26
+ export * from '@shadow-garden/bapbong-contracts';
27
+ export * from '@shadow-garden/bapbong-model';
28
+ export * from '@shadow-garden/bapbong-docx';
29
+ export * from '@shadow-garden/bapbong-commands';
30
+ export { layout, createLayoutCache } from '@shadow-garden/bapbong-layout-engine';
31
+ export { FontRegistry, createFontRegistryMeasurer, createFontRegistryMetrics, createApproxMeasurer, createApproxMetrics, fontToCss, type FontVariant, } from '@shadow-garden/bapbong-measuring';
32
+ export type { Align, PageConfig, CommentData } from '@shadow-garden/bapbong-contracts';
33
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;GAwBG;AACH,cAAc,kCAAkC,CAAC;AACjD,cAAc,8BAA8B,CAAC;AAC7C,cAAc,6BAA6B,CAAC;AAC5C,cAAc,iCAAiC,CAAC;AAChD,OAAO,EAAE,MAAM,EAAE,iBAAiB,EAAE,MAAM,sCAAsC,CAAC;AACjF,OAAO,EACL,YAAY,EACZ,0BAA0B,EAC1B,yBAAyB,EACzB,oBAAoB,EACpB,mBAAmB,EACnB,SAAS,EACT,KAAK,WAAW,GACjB,MAAM,kCAAkC,CAAC;AAM1C,YAAY,EAAE,KAAK,EAAE,UAAU,EAAE,WAAW,EAAE,MAAM,kCAAkC,CAAC"}
package/dist/index.js ADDED
@@ -0,0 +1,24 @@
1
+ // packages/headless/src/index.ts
2
+ export * from "@shadow-garden/bapbong-contracts";
3
+ export * from "@shadow-garden/bapbong-model";
4
+ export * from "@shadow-garden/bapbong-docx";
5
+ export * from "@shadow-garden/bapbong-commands";
6
+ import { layout, createLayoutCache } from "@shadow-garden/bapbong-layout-engine";
7
+ import {
8
+ FontRegistry,
9
+ createFontRegistryMeasurer,
10
+ createFontRegistryMetrics,
11
+ createApproxMeasurer,
12
+ createApproxMetrics,
13
+ fontToCss
14
+ } from "@shadow-garden/bapbong-measuring";
15
+ export {
16
+ FontRegistry,
17
+ createApproxMeasurer,
18
+ createApproxMetrics,
19
+ createFontRegistryMeasurer,
20
+ createFontRegistryMetrics,
21
+ createLayoutCache,
22
+ fontToCss,
23
+ layout
24
+ };
package/package.json ADDED
@@ -0,0 +1,75 @@
1
+ {
2
+ "name": "@shadow-garden/bapbong-headless",
3
+ "version": "0.1.0",
4
+ "description": "bapbong — headless backend façade: one install re-exporting contracts + model + docx + commands (isomorphic, no DOM). Import .docx → edit via commands on an EditorState → export .docx, server-side.",
5
+ "license": "MIT",
6
+ "repository": {
7
+ "type": "git",
8
+ "url": "git+https://github.com/shadowgarden-app/bapbong.git",
9
+ "directory": "packages/headless"
10
+ },
11
+ "type": "module",
12
+ "main": "./dist/index.cjs",
13
+ "module": "./dist/index.js",
14
+ "types": "./dist/index.d.ts",
15
+ "exports": {
16
+ "./package.json": "./package.json",
17
+ ".": {
18
+ "@shadow-garden/source": "./src/index.ts",
19
+ "types": "./dist/index.d.ts",
20
+ "import": "./dist/index.js",
21
+ "require": "./dist/index.cjs",
22
+ "default": "./dist/index.js"
23
+ }
24
+ },
25
+ "files": [
26
+ "dist",
27
+ "!**/*.tsbuildinfo"
28
+ ],
29
+ "publishConfig": {
30
+ "access": "public"
31
+ },
32
+ "nx": {
33
+ "tags": [
34
+ "scope:headless"
35
+ ],
36
+ "targets": {
37
+ "build": {
38
+ "executor": "@nx/esbuild:esbuild",
39
+ "outputs": [
40
+ "{options.outputPath}"
41
+ ],
42
+ "options": {
43
+ "outputPath": "packages/headless/dist",
44
+ "main": "packages/headless/src/index.ts",
45
+ "tsConfig": "packages/headless/tsconfig.lib.json",
46
+ "format": [
47
+ "esm",
48
+ "cjs"
49
+ ],
50
+ "declarationRootDir": "packages/headless/src",
51
+ "external": [
52
+ "@shadow-garden/bapbong-contracts",
53
+ "@shadow-garden/bapbong-model",
54
+ "@shadow-garden/bapbong-docx",
55
+ "@shadow-garden/bapbong-commands",
56
+ "@shadow-garden/bapbong-layout-engine",
57
+ "@shadow-garden/bapbong-measuring"
58
+ ]
59
+ }
60
+ }
61
+ }
62
+ },
63
+ "dependencies": {
64
+ "@shadow-garden/bapbong-contracts": "^0.1.0",
65
+ "@shadow-garden/bapbong-commands": "^0.1.0",
66
+ "@shadow-garden/bapbong-docx": "^0.1.0",
67
+ "@shadow-garden/bapbong-layout-engine": "^0.1.0",
68
+ "@shadow-garden/bapbong-measuring": "^0.1.0",
69
+ "@shadow-garden/bapbong-model": "^0.1.0"
70
+ },
71
+ "devDependencies": {
72
+ "prosemirror-state": "^1.4.4",
73
+ "opentype.js": "^2.0.0"
74
+ }
75
+ }