@cenk1cenk2/md-printer 3.2.24 → 3.4.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.
Files changed (54) hide show
  1. package/README.md +213 -57
  2. package/dist/_virtual/{_@oxc-project_runtime@0.156.0 → _@oxc-project_runtime@0.157.0}/helpers/esm/decorate.mjs +1 -1
  3. package/dist/_virtual/{_@oxc-project_runtime@0.156.0 → _@oxc-project_runtime@0.157.0}/helpers/esm/decorateMetadata.mjs +1 -1
  4. package/dist/_virtual/{_@oxc-project_runtime@0.156.0 → _@oxc-project_runtime@0.157.0}/helpers/esm/decorateParam.mjs +1 -1
  5. package/dist/commands/index.mjs +3 -1
  6. package/dist/components/Localized.svelte +18 -0
  7. package/dist/components/SignatureBlock.svelte +8 -46
  8. package/dist/components/Translate.svelte +15 -0
  9. package/dist/components/extension.ts +8 -0
  10. package/dist/components/index.ts +3 -0
  11. package/dist/constants/attachment.constants.mjs +7 -0
  12. package/dist/constants/index.mjs +3 -2
  13. package/dist/constants/template.constants.mjs +26 -2
  14. package/dist/interfaces/attachment.interface.mjs +1 -0
  15. package/dist/modules/md-printer/md-printer.handler.mjs +4 -2
  16. package/dist/modules/md-printer/md-printer.module.mjs +1 -1
  17. package/dist/modules/md-printer/md-printer.schema.mjs +12 -1
  18. package/dist/services/i18n.service.mjs +6 -4
  19. package/dist/services/index.mjs +2 -1
  20. package/dist/services/markdown.service.mjs +1 -1
  21. package/dist/services/pdf/pdf.service.mjs +124 -0
  22. package/dist/services/printer.module.mjs +3 -1
  23. package/dist/services/printer.service.mjs +55 -11
  24. package/dist/services/renderer/browser.service.mjs +3 -3
  25. package/dist/services/renderer/renderer.service.mjs +3 -3
  26. package/dist/services/session/preview.service.mjs +2 -2
  27. package/dist/services/session/session.service.mjs +11 -11
  28. package/dist/services/signature/adapters/a-trust.adapter.mjs +2 -2
  29. package/dist/services/signature/signature.service.mjs +2 -2
  30. package/dist/services/template/assets.mjs +1 -1
  31. package/dist/services/template/render.entry.ts +6 -2
  32. package/dist/services/template/svelte.plugin.mjs +12 -7
  33. package/dist/services/template/template.schema.mjs +27 -0
  34. package/dist/services/template/template.service.mjs +123 -26
  35. package/oclif.manifest.json +16 -2
  36. package/package.json +14 -24
  37. package/templates/default/Template.svelte +0 -83
  38. package/templates/default/settings.json +0 -7
  39. package/templates/invoice/Template.svelte +0 -247
  40. package/templates/invoice/components/Client.svelte +0 -42
  41. package/templates/invoice/components/Company.svelte +0 -41
  42. package/templates/invoice/components/Items.svelte +0 -66
  43. package/templates/invoice/components/Notes.svelte +0 -21
  44. package/templates/invoice/components/Payment.svelte +0 -25
  45. package/templates/invoice/components/Signature.svelte +0 -34
  46. package/templates/invoice/components/Totals.svelte +0 -47
  47. package/templates/invoice/i18n/de.yaml +0 -30
  48. package/templates/invoice/i18n/en.yaml +0 -30
  49. package/templates/invoice/round.js +0 -2
  50. package/templates/invoice/settings.json +0 -11
  51. package/templates/kilic.dev/Template.svelte +0 -102
  52. package/templates/kilic.dev/settings.json +0 -7
  53. package/templates/mail/Template.svelte +0 -166
  54. package/templates/mail/settings.json +0 -7
@@ -0,0 +1,27 @@
1
+ import { TemplateSourceType } from "../../constants/template.constants.mjs";
2
+ import { z } from "zod";
3
+ const TemplateSourceSchema = z.discriminatedUnion("type", [
4
+ z.strictObject({
5
+ type: z.literal("builtin"),
6
+ name: z.string().regex(/^[^\\/]+$/, "Built-in template names have no path separator.")
7
+ }),
8
+ z.strictObject({
9
+ type: z.literal("package"),
10
+ name: z.string().regex(/^(@[a-z0-9-~][a-z0-9-._~]*\/)?[a-z0-9-~][a-z0-9-._~]*$/, "Not an npm package name."),
11
+ directory: z.string().optional()
12
+ }),
13
+ z.strictObject({
14
+ type: z.literal("directory"),
15
+ path: z.string().min(1)
16
+ })
17
+ ], { error: () => `Use a string or an object with a type of ${Object.values(TemplateSourceType).join(", ")}.` });
18
+ const TemplateSettingsSchema = z.looseObject({ files: z.strictObject({
19
+ template: z.string().min(1).optional(),
20
+ components: z.union([z.string().min(1), z.array(z.string().min(1)).min(1)]).optional(),
21
+ extension: z.union([z.string().min(1), z.array(z.string().min(1)).min(1)]).optional(),
22
+ i18n: z.union([z.string().min(1), z.array(z.string().min(1)).min(1)]).optional()
23
+ }).optional() });
24
+ function issues({ issues }) {
25
+ return issues.map(({ path, message }) => [...path, message].join(": ")).join(", ");
26
+ }
27
+ export { TemplateSettingsSchema, TemplateSourceSchema, issues };
@@ -1,12 +1,13 @@
1
- import { inlineCss, inlineHtml } from "./assets.mjs";
1
+ import { inlineCss, inlineHtml, resolveConfined } from "./assets.mjs";
2
2
  import { sveltePlugin } from "./svelte.plugin.mjs";
3
- import "../../constants/template.constants.mjs";
4
- import __decorateMetadata from "../../_virtual/_@oxc-project_runtime@0.156.0/helpers/esm/decorateMetadata.mjs";
5
- import __decorate from "../../_virtual/_@oxc-project_runtime@0.156.0/helpers/esm/decorate.mjs";
3
+ import { TemplateSettingsSchema, issues } from "./template.schema.mjs";
4
+ import { TEMPLATE_EXTENSION_FILES, TEMPLATE_LAYOUT, TEMPLATE_PACKAGE_PREFIX } from "../../constants/template.constants.mjs";
5
+ import __decorateMetadata from "../../_virtual/_@oxc-project_runtime@0.157.0/helpers/esm/decorateMetadata.mjs";
6
+ import __decorate from "../../_virtual/_@oxc-project_runtime@0.157.0/helpers/esm/decorate.mjs";
6
7
  import { Injectable } from "@nestjs/common";
7
- import { dirname, isAbsolute, join, resolve } from "path";
8
+ import { dirname, isAbsolute, join, relative, resolve, sep } from "path";
8
9
  import { FileSystemService } from "@cenk1cenk2/oclif-common";
9
- import { fileURLToPath } from "url";
10
+ import { fileURLToPath, pathToFileURL } from "url";
10
11
  import { homedir } from "os";
11
12
  import { compile } from "@tailwindcss/node";
12
13
  import { Scanner } from "@tailwindcss/oxide";
@@ -45,21 +46,20 @@ let TemplateService = class TemplateService {
45
46
  constructor(fs) {
46
47
  this.fs = fs;
47
48
  }
48
- resolve(template) {
49
- const path = template.replace(/^~(?=\/|$)/, homedir());
50
- const directory = isAbsolute(path) || path.startsWith(".") || /[\\/]/.test(path) ? resolve(path) : join(_TemplateService.ROOT, "templates", path);
51
- if (!this.fs.exists(join(directory, "Template.svelte"))) throw new Error(`Template does not exist, expected Template.svelte in: ${directory}`);
52
- return directory;
53
- }
54
- async settings(directory) {
55
- const file = join(directory, "settings.json");
56
- if (!this.fs.exists(file)) return {};
57
- return JSON.parse(await this.fs.read(file));
49
+ async resolve(template, base) {
50
+ const directory = await this.locate(template, base);
51
+ const settings = await this.settings(directory);
52
+ return {
53
+ directory,
54
+ settings,
55
+ files: await this.paths(directory, settings.files)
56
+ };
58
57
  }
59
- async bundle(directory) {
58
+ async bundle(files) {
60
59
  const stylesheets = [];
61
- const { module: entry, modules } = await this.compile(_TemplateService.ENTRY, join(directory, "Template.svelte"), stylesheets);
60
+ const { module: entry, modules } = await this.compile(_TemplateService.ENTRY, stylesheets, files);
62
61
  return {
62
+ template: files.template,
63
63
  entry,
64
64
  modules,
65
65
  stylesheets,
@@ -67,17 +67,22 @@ let TemplateService = class TemplateService {
67
67
  };
68
68
  }
69
69
  async page(file) {
70
- const { module } = await this.compile(file, file, []);
70
+ const { module } = await this.compile(file, [], {
71
+ directory: dirname(file),
72
+ template: file
73
+ });
71
74
  return `<!doctype html>${render(module.default).body}`;
72
75
  }
73
76
  async render(directory, bundle, document, markdown, options) {
74
77
  const context = [
75
78
  ["md-printer:document", document],
76
79
  ["md-printer:markdown", markdown],
77
- ["md-printer:components", bundle.entry.components]
80
+ ["md-printer:components", bundle.entry.components],
81
+ ["md-printer:extension", bundle.entry.extension]
78
82
  ];
79
83
  const props = {
80
84
  ...document,
85
+ extension: bundle.entry.extension,
81
86
  content: bundle.entry.content(markdown, context)
82
87
  };
83
88
  const [body, header, footer] = await Promise.all([
@@ -108,16 +113,107 @@ let TemplateService = class TemplateService {
108
113
  dependencies
109
114
  };
110
115
  }
111
- async compile(input, template, stylesheets) {
116
+ locate(template, base) {
117
+ if (typeof template === "string") {
118
+ const path = this.expand(template);
119
+ return isAbsolute(path) || path.startsWith(".") || /[\\/]/.test(path) ? resolve(path) : this.builtin(path);
120
+ }
121
+ switch (template.type) {
122
+ case "builtin": return this.builtin(template.name);
123
+ case "package": return this.package(template, base);
124
+ case "directory": return resolve(base, this.expand(template.path));
125
+ }
126
+ }
127
+ expand(path) {
128
+ return path.replace(/^~(?=\/|$)/, homedir());
129
+ }
130
+ /** A built-in template is a package of its own, so it brings its own fonts, icons and stylesheets as dependencies. */
131
+ builtin(name) {
132
+ const pkg = `${TEMPLATE_PACKAGE_PREFIX}${name}`;
133
+ try {
134
+ return dirname(this.require.resolve(`${pkg}/package.json`));
135
+ } catch {
136
+ throw new Error(`Template does not exist, expected the built-in template package ${pkg} or a path to a template directory.`);
137
+ }
138
+ }
139
+ async package({ name, directory }, base) {
140
+ const root = this.installed(name, [.../* @__PURE__ */ new Set([base, process.cwd()]), _TemplateService.ROOT]);
141
+ if (directory === void 0) return root;
142
+ const confined = await resolveConfined(resolve(root, directory), root);
143
+ if (!confined) throw new Error(`Template directory "${directory}" of the package ${name} has to exist inside the package: ${root}`);
144
+ return confined;
145
+ }
146
+ installed(name, roots) {
147
+ for (const root of roots) try {
148
+ return dirname(createRequire(join(root, "package.json")).resolve(`${name}/package.json`));
149
+ } catch {
150
+ continue;
151
+ }
152
+ throw new Error(`Template does not exist, the package ${name} is not installed in any of: ${roots.join(", ")}`);
153
+ }
154
+ async settings(directory) {
155
+ const file = join(directory, "settings.json");
156
+ if (!this.fs.exists(file)) return {};
157
+ const { success, data, error } = TemplateSettingsSchema.safeParse(JSON.parse(await this.fs.read(file)));
158
+ if (!success) throw new Error(`Template settings are invalid in ${file}: ${issues(error)}`);
159
+ return data;
160
+ }
161
+ async paths(directory, files = {}) {
162
+ const template = files.template ? await this.configured(directory, "template", files.template) : this.first(directory, TEMPLATE_LAYOUT.template);
163
+ const components = files.components ? await Promise.all([files.components].flat().map((path) => this.configured(directory, "components", path))) : [this.first(directory, TEMPLATE_LAYOUT.components) ?? join(directory, TEMPLATE_LAYOUT.components[0])];
164
+ const i18n = files.i18n ? await Promise.all([files.i18n].flat().map((path) => this.configured(directory, "i18n", path))) : [this.first(directory, TEMPLATE_LAYOUT.i18n) ?? join(directory, TEMPLATE_LAYOUT.i18n[0])];
165
+ const extension = files.extension ? await Promise.all([files.extension].flat().map((path) => this.configured(directory, "extension", path))) : [this.extension(directory)].filter((path) => path !== void 0);
166
+ if (!template) throw new Error(`Template does not exist, expected ${TEMPLATE_LAYOUT.template.join(" or ")} in: ${directory}`);
167
+ return {
168
+ directory,
169
+ template,
170
+ components,
171
+ i18n,
172
+ extension,
173
+ candidates: [
174
+ ...files.template ? [template] : TEMPLATE_LAYOUT.template.map((path) => join(directory, path)),
175
+ ...files.components ? components : TEMPLATE_LAYOUT.components.map((path) => join(directory, path)),
176
+ ...files.i18n ? i18n : TEMPLATE_LAYOUT.i18n.map((path) => join(directory, path)),
177
+ ...files.extension ? extension : TEMPLATE_LAYOUT.extension.flatMap((path) => TEMPLATE_EXTENSION_FILES.map((file) => join(directory, path, file)))
178
+ ]
179
+ };
180
+ }
181
+ async configured(directory, key, value) {
182
+ const path = resolve(directory, value);
183
+ const rel = relative(directory, path);
184
+ const outside = rel === ".." || rel.startsWith(`..${sep}`) || isAbsolute(rel);
185
+ if (!outside && !this.fs.exists(path)) throw new Error(`Template settings point files.${key} to a path that does not exist: ${path}`);
186
+ if (outside || !await resolveConfined(path, directory)) throw new Error(`Template settings point files.${key} outside of the template directory: ${value}`);
187
+ return path;
188
+ }
189
+ first(directory, paths) {
190
+ return paths.map((path) => join(directory, path)).find((path) => this.fs.exists(path));
191
+ }
192
+ extension(directory) {
193
+ for (const location of TEMPLATE_LAYOUT.extension) {
194
+ const files = TEMPLATE_EXTENSION_FILES.filter((file) => this.fs.exists(join(directory, location, file)));
195
+ if (files.length > 1) throw new Error(`Template has more than one extension module, keep one of ${files.join(", ")} in: ${join(directory, location)}`);
196
+ if (files.length === 1) return join(directory, location, files[0]);
197
+ }
198
+ }
199
+ async compile(input, stylesheets, files) {
112
200
  const build = await rolldown({
113
201
  input,
114
202
  platform: "node",
115
- logLevel: "silent",
203
+ logLevel: "warn",
204
+ onLog(_, log, handler) {
205
+ if (log.code === "UNRESOLVED_IMPORT") handler("error", {
206
+ ...log,
207
+ message: `${log.message} Install it in the template directory: ${files.directory}`
208
+ });
209
+ },
116
210
  plugins: [sveltePlugin({
117
- template,
211
+ template: files.template,
118
212
  components: _TemplateService.COMPONENTS,
213
+ templateComponents: files.components,
119
214
  root: _TemplateService.ROOT,
120
- stylesheets
215
+ stylesheets,
216
+ extension: files.extension
121
217
  })]
122
218
  });
123
219
  try {
@@ -125,8 +221,9 @@ let TemplateService = class TemplateService {
125
221
  format: "esm",
126
222
  sourcemap: "inline"
127
223
  });
224
+ const code = chunk.code.replaceAll("createRequire(import.meta.url)", `createRequire(${JSON.stringify(pathToFileURL(files.template).href)})`);
128
225
  return {
129
- module: await import(`data:text/javascript;base64,${Buffer.from(chunk.code).toString("base64")}`),
226
+ module: await import(`data:text/javascript;base64,${Buffer.from(code).toString("base64")}`),
130
227
  modules: chunk.moduleIds.filter((id) => isAbsolute(id))
131
228
  };
132
229
  } finally {
@@ -149,7 +246,7 @@ let TemplateService = class TemplateService {
149
246
  const theme = `:root { ${readFileSync(this.highlightTheme(highlight), "utf8")} pre:has(> code.hljs) { padding: 0; background: transparent; } }`;
150
247
  const compiler = await compile([theme, ...bundle.stylesheets.map(({ source }) => source)].join("\n"), {
151
248
  base: directory,
152
- from: bundle.stylesheets[0]?.file ?? join(directory, "Template.svelte"),
249
+ from: bundle.stylesheets[0]?.file ?? bundle.template,
153
250
  shouldRewriteUrls: true,
154
251
  onDependency: (path) => dependencies.push(path),
155
252
  customCssResolver: async (id, base) => this.resolveFrom(this.stylesheets, id, [
@@ -94,12 +94,26 @@
94
94
  },
95
95
  "template": {
96
96
  "char": "t",
97
- "description": "Built-in template name or path to a template directory, defaults to \"default\". Overwrites the one defined in front-matter.",
97
+ "description": "Built-in template name or path to a template directory, defaults to \"default\", read as --template-type when given. Overwrites the one defined in front-matter.",
98
98
  "name": "template",
99
99
  "hasDynamicHelp": false,
100
100
  "multiple": false,
101
101
  "type": "option"
102
102
  },
103
+ "template-type": {
104
+ "description": "How to read --template, one of builtin, package or directory, like the type of the object form in front-matter.",
105
+ "name": "template-type",
106
+ "hasDynamicHelp": false,
107
+ "multiple": false,
108
+ "type": "option"
109
+ },
110
+ "template-directory": {
111
+ "description": "Directory inside the package to use as the template, only valid with --template-type package.",
112
+ "name": "template-directory",
113
+ "hasDynamicHelp": false,
114
+ "multiple": false,
115
+ "type": "option"
116
+ },
103
117
  "title": {
104
118
  "char": "T",
105
119
  "description": "Document title. Overwrites the one defined in front-matter or the template.",
@@ -198,5 +212,5 @@
198
212
  "enableJsonFlag": false
199
213
  }
200
214
  },
201
- "version": "3.2.24"
215
+ "version": "3.4.0"
202
216
  }
package/package.json CHANGED
@@ -1,11 +1,12 @@
1
1
  {
2
2
  "name": "@cenk1cenk2/md-printer",
3
- "version": "3.2.24",
3
+ "version": "3.4.0",
4
4
  "description": "Render markdown or yaml through Svelte templates into PDF or HTML with Puppeteer.",
5
5
  "type": "module",
6
6
  "repository": {
7
7
  "type": "git",
8
- "url": "https://gitlab.kilic.dev/utils/md-printer.git"
8
+ "url": "https://gitlab.kilic.dev/utils/md-printer.git",
9
+ "directory": "packages/md-printer"
9
10
  },
10
11
  "author": "Cenk Kilic",
11
12
  "license": "MIT",
@@ -18,8 +19,7 @@
18
19
  "files": [
19
20
  "/bin",
20
21
  "/dist",
21
- "/oclif.manifest.json",
22
- "templates/"
22
+ "/oclif.manifest.json"
23
23
  ],
24
24
  "oclif": {
25
25
  "bin": "md-printer",
@@ -49,11 +49,15 @@
49
49
  "cenk1cenk2"
50
50
  ],
51
51
  "dependencies": {
52
+ "@cenk1cenk2/md-printer-template-cv": "^1.0.0",
53
+ "@cenk1cenk2/md-printer-template-default": "1.1.0",
54
+ "@cenk1cenk2/md-printer-template-invoice": "^1.0.0",
55
+ "@cenk1cenk2/md-printer-template-kilic.dev": "1.1.0",
56
+ "@cenk1cenk2/md-printer-template-mail": "1.1.0",
52
57
  "@cenk1cenk2/oclif-common": "^8.0.2",
53
- "@fontsource/montserrat": "^5.3.0",
54
58
  "@listr2/manager": "^4.3.3",
55
59
  "@nestjs/common": "^12.3.2",
56
- "@oclif/core": "^5.1.10",
60
+ "@oclif/core": "^5.1.11",
57
61
  "@oclif/plugin-help": "^7.0.6",
58
62
  "@signpdf/placeholder-plain": "^4.0.0",
59
63
  "@signpdf/utils": "^4.0.0",
@@ -66,15 +70,15 @@
66
70
  "enhanced-resolve": "^5.26.0",
67
71
  "entities": "^9.0.0",
68
72
  "es-toolkit": "^1.53.1",
69
- "github-markdown-css": "^5.9.0",
70
73
  "hast-util-from-html": "^2.0.3",
71
74
  "hast-util-to-html": "^9.0.6",
72
75
  "highlight.js": "^11.12.0",
73
- "i18next": "^26.5.12",
76
+ "i18next": "^26.7.1",
74
77
  "lightningcss": "^1.33.0",
75
78
  "listr2": "^11.4.0",
76
79
  "lowlight": "^3.3.0",
77
80
  "mime": "^4.1.2",
81
+ "mupdf": "^1.28.1",
78
82
  "perfect-debounce": "^2.1.0",
79
83
  "pkijs": "^4.0.1",
80
84
  "property-information": "^7.2.0",
@@ -105,33 +109,21 @@
105
109
  "zod": "^4.6.7"
106
110
  },
107
111
  "devDependencies": {
108
- "@cenk1cenk2/cz-cc": "^3.0.12",
109
- "@cenk1cenk2/eslint-config": "^3.4.5",
110
112
  "@tsconfig/node24": "^24.0.5",
111
113
  "@types/hast": "^3.0.5",
112
114
  "@types/mdast": "^4.0.4",
113
- "@types/node": "^26.6.5",
115
+ "@types/node": "^26.6.6",
114
116
  "@types/serve-static": "^2.2.0",
115
117
  "@types/which": "^3.0.4",
116
118
  "@types/write-file-atomic": "^4.0.3",
117
- "eslint": "^10.13.0",
118
- "eslint-plugin-svelte": "^3.23.1",
119
119
  "execa": "^10.2.1",
120
120
  "oclif": "^6.0.15",
121
- "prettier": "^3.9.10",
122
- "prettier-plugin-svelte": "^4.1.1",
123
- "svelte-eslint-parser": "^1.10.0",
124
121
  "ts-node": "^10.9.2",
125
122
  "tsconfig-paths": "^4.2.0",
126
123
  "tsdown": "^0.23.4",
127
124
  "typescript": "^6.0.3",
128
125
  "vite": "^8.3.5",
129
- "vitest": "^5.0.5"
130
- },
131
- "config": {
132
- "commitizen": {
133
- "path": "./node_modules/@cenk1cenk2/cz-cc"
134
- }
126
+ "vitest": "^5.1.0"
135
127
  },
136
128
  "bugs": {
137
129
  "url": "https://gitlab.kilic.dev/utils/md-printer/-/issues"
@@ -142,8 +134,6 @@
142
134
  "start": "./bin/run.js",
143
135
  "build": "tsdown",
144
136
  "dev:start": "tsdown --watch src/",
145
- "format": "prettier --write src/ --log-level warn && eslint --fix",
146
- "lint": "eslint",
147
137
  "manifest": "oclif manifest",
148
138
  "typecheck": "tsc --noEmit",
149
139
  "test": "vitest run"
@@ -1,83 +0,0 @@
1
- <script>
2
- import { Markdown, Page } from '@cenk1cenk2/md-printer/components'
3
-
4
- let { data } = $props()
5
- </script>
6
-
7
- <svelte:head>
8
- {#if data.documentTitle}
9
- <title>{data.documentTitle}</title>
10
- {/if}
11
- </svelte:head>
12
-
13
- <Page>
14
- <Markdown />
15
- </Page>
16
-
17
- <style lang="postcss">
18
- @import 'github-markdown-css/github-markdown-light.css';
19
- @import '@fontsource/montserrat/latin-400.css';
20
- @import '@fontsource/montserrat/latin-ext-400.css';
21
- @import '@fontsource/montserrat/latin-700.css';
22
- @import '@fontsource/montserrat/latin-ext-700.css';
23
- @import '@fontsource/montserrat/latin-800.css';
24
- @import '@fontsource/montserrat/latin-ext-800.css';
25
-
26
- .markdown-body {
27
- font-size: 11px;
28
- font-family: 'Montserrat', sans-serif;
29
- }
30
-
31
- .markdown-body h1,
32
- .markdown-body h2 {
33
- font-weight: 800;
34
- }
35
-
36
- .markdown-body h3,
37
- .markdown-body h4,
38
- .markdown-body h5,
39
- .markdown-body h6,
40
- .markdown-body strong,
41
- .markdown-body b {
42
- font-weight: 700;
43
- }
44
-
45
- .markdown-body pre > code {
46
- white-space: pre-wrap;
47
- padding: 0;
48
- margin: 0;
49
- }
50
-
51
- .markdown-body .document-title-header {
52
- height: 500px;
53
- margin: auto auto;
54
- padding-top: 50%;
55
- break-after: page;
56
- border-bottom: 0;
57
- font-size: 2.5em;
58
- }
59
-
60
- .markdown-body pre {
61
- padding: 12px 8px;
62
- }
63
-
64
- .markdown-body output pre {
65
- margin-top: -36px;
66
- border-top-left-radius: 0;
67
- border-top-right-radius: 0;
68
- border-top: 2px solid #d1d9e0;
69
- }
70
-
71
- .markdown-body output::before {
72
- padding: 4px 16px;
73
- position: relative;
74
- top: -24px;
75
- border-top-left-radius: 4px;
76
- border-top-right-radius: 4px;
77
- border-top: 2px solid #d1d9e0;
78
- color: #59636e;
79
- background-color: #f6f8fa;
80
- content: '> output';
81
- font-size: 0.85em;
82
- }
83
- </style>
@@ -1,7 +0,0 @@
1
- {
2
- "pdfOptions": {
3
- "format": "A4",
4
- "margin": "18mm 12mm",
5
- "printBackground": true
6
- }
7
- }