mirror of
https://github.com/andy-stack/vaultkeeper-ai.git
synced 2026-07-22 06:42:03 +00:00
refactor: replace mammoth with native DOCX parser using fflate
Remove mammoth dependency and implement lightweight DOCX text extraction using fflate + DOMParser. Extracts text from body, headers/footers, and footnotes/endnotes by parsing w:p/w:t elements. Make readDocument() synchronous. Add PDF.js type definitions to eliminate unsafe any access.
This commit is contained in:
parent
cf037a09de
commit
6835c9167d
8 changed files with 68 additions and 243 deletions
|
|
@ -1,13 +1,30 @@
|
|||
import { loadPdfJs } from 'obsidian';
|
||||
import { unzipSync, strFromU8 } from 'fflate';
|
||||
import mammoth from 'mammoth/mammoth.browser.js';
|
||||
import type { IPageText } from '../Types/SearchTypes';
|
||||
import { Exception } from './Exception';
|
||||
|
||||
// Minimal structural types for the slice of PDF.js we use. Obsidian's `loadPdfJs()`
|
||||
// is typed as `Promise<any>` and we don't bundle pdfjs-dist, so we describe just the
|
||||
// shape we touch to keep this file free of unsafe-`any` access.
|
||||
interface PdfTextItem { str?: string; }
|
||||
interface PdfTextContent { items: PdfTextItem[]; }
|
||||
interface PdfPage {
|
||||
getTextContent(): Promise<PdfTextContent>;
|
||||
cleanup?(): void;
|
||||
}
|
||||
interface PdfDocument {
|
||||
numPages: number;
|
||||
getPage(pageNumber: number): Promise<PdfPage>;
|
||||
destroy?(): Promise<void>;
|
||||
}
|
||||
interface PdfJs {
|
||||
getDocument(src: { data: Uint8Array }): { promise: Promise<PdfDocument> };
|
||||
}
|
||||
|
||||
// Uses Obsidian's own bundled PDF.js via loadPdfJs() rather than shipping our own
|
||||
export async function readPDF(arrayBuffer: ArrayBuffer): Promise<IPageText[]> {
|
||||
try {
|
||||
const pdfjs = await loadPdfJs();
|
||||
const pdfjs = (await loadPdfJs()) as PdfJs;
|
||||
const pdf = await pdfjs.getDocument({ data: new Uint8Array(arrayBuffer) }).promise;
|
||||
|
||||
const pageTexts: IPageText[] = [];
|
||||
|
|
@ -15,7 +32,7 @@ export async function readPDF(arrayBuffer: ArrayBuffer): Promise<IPageText[]> {
|
|||
const page = await pdf.getPage(i);
|
||||
const content = await page.getTextContent();
|
||||
const text = content.items
|
||||
.map((item: { str?: string }) => item.str ?? '')
|
||||
.map((item) => item.str ?? '')
|
||||
.join(' ');
|
||||
pageTexts.push({ text, pageNumber: i });
|
||||
page.cleanup?.();
|
||||
|
|
@ -41,16 +58,15 @@ export async function readPDF(arrayBuffer: ArrayBuffer): Promise<IPageText[]> {
|
|||
|
||||
// Handles document formats: DOCX, PPTX, XLSX, ODT, ODP, ODS.
|
||||
//
|
||||
// DOCX goes through mammoth (battle-tested: tables, lists, footnotes). The remaining
|
||||
// formats are ZIP-of-XML containers we read with fflate + the platform DOMParser, so
|
||||
// no heavy parser is bundled. We only extract plain text (no OCR, no images) — the LLM
|
||||
// can read files directly and use its own vision engine when it needs to.
|
||||
export async function readDocument(arrayBuffer: ArrayBuffer, extension: string): Promise<IPageText[]> {
|
||||
// Every format is a ZIP-of-XML container we read with fflate + the platform DOMParser,
|
||||
// so no heavy parser is bundled. We only extract plain text (no OCR, no images) — the
|
||||
// LLM can read files directly and use its own vision engine when it needs to.
|
||||
export function readDocument(arrayBuffer: ArrayBuffer, extension: string): IPageText[] {
|
||||
try {
|
||||
let text: string;
|
||||
switch (extension.toLowerCase()) {
|
||||
case 'docx':
|
||||
text = (await mammoth.extractRawText({ arrayBuffer })).value;
|
||||
text = extractDocx(arrayBuffer);
|
||||
break;
|
||||
case 'xlsx':
|
||||
text = extractXlsx(arrayBuffer);
|
||||
|
|
@ -74,7 +90,7 @@ export async function readDocument(arrayBuffer: ArrayBuffer, extension: string):
|
|||
}
|
||||
}
|
||||
|
||||
// --- Shared helpers for the ZIP-of-XML formats (xlsx / pptx / odf) ---
|
||||
// --- Shared helpers for the ZIP-of-XML formats (docx / xlsx / pptx / odf) ---
|
||||
|
||||
// Throws on legacy OLE2 binaries (.xls/.ppt/.doc) — they aren't ZIPs. Callers wrap
|
||||
// this so the failure surfaces as a clean "failed to read" message.
|
||||
|
|
@ -92,6 +108,40 @@ function ordinal(path: string): number {
|
|||
return match ? Number(match[1]) : 0;
|
||||
}
|
||||
|
||||
// --- DOCX: body in word/document.xml; <w:p> = paragraph, <w:t> = text run.
|
||||
// Headers/footers and foot/endnotes live in sibling parts that share the same
|
||||
// <w:p>/<w:t> shape, so they run through the same paragraph extractor. ---
|
||||
function extractDocx(arrayBuffer: ArrayBuffer): string {
|
||||
const files = unzip(arrayBuffer);
|
||||
|
||||
// Joined text of every <w:p> paragraph in a parsed part. Runs are joined with
|
||||
// '' (not a space) because Word splits a single word across multiple <w:t> runs
|
||||
// for spell-check / formatting — a space here would shred words like "Hel"+"lo".
|
||||
// Empty paragraphs (incl. the separator entries in foot/endnotes) are dropped.
|
||||
const paragraphs = (bytes: Uint8Array): string =>
|
||||
Array.from(parseXml(bytes).getElementsByTagName('w:p'))
|
||||
.map((p) =>
|
||||
Array.from(p.getElementsByTagName('w:t'))
|
||||
.map((t) => t.textContent ?? '')
|
||||
.join('')
|
||||
)
|
||||
.filter((line) => line.length > 0)
|
||||
.join('\n');
|
||||
|
||||
// Body first, then headers/footers (grouped + numerically ordered), then notes.
|
||||
const headerFooter = Object.keys(files)
|
||||
.filter((name) => /^word\/(header|footer)\d+\.xml$/.test(name))
|
||||
.sort();
|
||||
|
||||
const parts: string[] = [];
|
||||
if (files['word/document.xml']) parts.push(paragraphs(files['word/document.xml']));
|
||||
for (const name of headerFooter) parts.push(paragraphs(files[name]));
|
||||
if (files['word/footnotes.xml']) parts.push(paragraphs(files['word/footnotes.xml']));
|
||||
if (files['word/endnotes.xml']) parts.push(paragraphs(files['word/endnotes.xml']));
|
||||
|
||||
return parts.filter((p) => p.length > 0).join('\n\n');
|
||||
}
|
||||
|
||||
// --- XLSX: values live as indices into a shared-strings table ---
|
||||
function extractXlsx(arrayBuffer: ArrayBuffer): string {
|
||||
const files = unzip(arrayBuffer);
|
||||
|
|
@ -172,4 +222,4 @@ function extractOdf(arrayBuffer: ArrayBuffer): string {
|
|||
}
|
||||
}
|
||||
return out.join('\n');
|
||||
}
|
||||
}
|
||||
|
|
@ -410,8 +410,7 @@ This plugin is built on the shoulders of many excellent projects:
|
|||
- Official SDKs: [@anthropic-ai/sdk](https://github.com/anthropics/anthropic-sdk-typescript), [@google/genai](https://github.com/google/generative-ai-js), [openai](https://github.com/openai/openai-node)
|
||||
|
||||
**Document Processing**
|
||||
- [mammoth](https://github.com/mwilliamson/mammoth.js) - DOCX text extraction
|
||||
- [fflate](https://github.com/101arrowz/fflate) - Unzipping Office Open XML / OpenDocument files (PPTX, XLSX, ODT, ODP, ODS)
|
||||
- [fflate](https://github.com/101arrowz/fflate) - Unzipping Office Open XML / OpenDocument files for text extraction (DOCX, PPTX, XLSX, ODT, ODP, ODS)
|
||||
- PDF text extraction via Obsidian's bundled [PDF.js](https://mozilla.github.io/pdf.js/) (`loadPdfJs()`)
|
||||
|
||||
**UI Framework**
|
||||
|
|
|
|||
|
|
@ -48,7 +48,7 @@ export class InputService {
|
|||
}
|
||||
|
||||
if (isDocumentFile(fileType)) {
|
||||
const content = await readDocument(await file.arrayBuffer(), fileType);
|
||||
const content = readDocument(await file.arrayBuffer(), fileType);
|
||||
attachments.push(new Attachment(
|
||||
file.name,
|
||||
MimeType.TEXT_PLAIN,
|
||||
|
|
|
|||
|
|
@ -98,7 +98,7 @@ export class VaultService {
|
|||
if (isDocumentFile(fileExtension)) {
|
||||
const arrayBuffer = await this.readBinaryData(file, allowAccessToPluginRoot);
|
||||
if (arrayBuffer) {
|
||||
return (await readDocument(arrayBuffer, fileExtension))[0].text;
|
||||
return (readDocument(arrayBuffer, fileExtension))[0].text;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -418,7 +418,7 @@ export class VaultService {
|
|||
content = await readPDF(arrayBuffer);
|
||||
} else if (isDocumentFile(fileExtension)) {
|
||||
const arrayBuffer = await this.vault.readBinary(file);
|
||||
content = await readDocument(arrayBuffer, fileExtension);
|
||||
content = readDocument(arrayBuffer, fileExtension);
|
||||
} else {
|
||||
content = [{ text: await this.vault.cachedRead(file), pageNumber: 1 }] as IPageText[];
|
||||
}
|
||||
|
|
|
|||
|
|
@ -43,11 +43,6 @@ function copyDir(src, dest) {
|
|||
//
|
||||
// All such literals come from dependencies, never from our own source, and every
|
||||
// one is dead code in our usage:
|
||||
// - bluebird (transitive via mammoth): 7x promise-method JIT compilers, ALL
|
||||
// gated behind `canEvaluate = typeof navigator == "undefined"`. Obsidian always
|
||||
// defines `navigator`, so `canEvaluate` is false and bluebird takes its pure-JS
|
||||
// fallbacks — the `new Function` branches are never entered. (call_get.js x2,
|
||||
// join.js x3, promisify.js x2.)
|
||||
// - diff2html/@profoundlogic/hogan: 2x template compilers reachable only via
|
||||
// Hogan.compile(), which diff2html invokes only for runtime `rawTemplates`.
|
||||
// We use diff2html's precompiled defaults, so these never run.
|
||||
|
|
@ -57,8 +52,8 @@ function copyDir(src, dest) {
|
|||
// build FAILS if the count drifts from EXPECTED_NEW_FUNCTION_COUNT, so a dependency
|
||||
// change can never silently reintroduce a live (or un-neutralised) dynamic-eval path.
|
||||
//
|
||||
// 9 = 7 bluebird (canEvaluate-gated) + 2 Hogan.
|
||||
const EXPECTED_NEW_FUNCTION_COUNT = 9;
|
||||
// 2 = Hogan.
|
||||
const EXPECTED_NEW_FUNCTION_COUNT = 2;
|
||||
const NEW_FUNCTION_STUB = "VKBlockedDynamicFn";
|
||||
function neutraliseDynamicEval(outfile) {
|
||||
if (!existsSync(outfile)) return;
|
||||
|
|
|
|||
10
global.d.ts
vendored
10
global.d.ts
vendored
|
|
@ -11,12 +11,4 @@ declare module '*.svg' {
|
|||
declare module '*.png' {
|
||||
const content: string;
|
||||
export default content;
|
||||
}
|
||||
|
||||
// mammoth ships type declarations for its default entry but not for the browser
|
||||
// build we import (mammoth/mammoth.browser.js) for mobile safety. The browser build
|
||||
// exposes the same public API, so we re-use mammoth's own types.
|
||||
declare module 'mammoth/mammoth.browser.js' {
|
||||
import mammoth from 'mammoth';
|
||||
export = mammoth;
|
||||
}
|
||||
}
|
||||
210
package-lock.json
generated
210
package-lock.json
generated
|
|
@ -21,7 +21,6 @@
|
|||
"highlight.js": "^11.11.1",
|
||||
"katex": "^0.17.0",
|
||||
"lowlight": "^3.3.0",
|
||||
"mammoth": "^1.12.0",
|
||||
"openai": "^6.45.0",
|
||||
"path-browserify": "^1.0.1",
|
||||
"regex-parser": "^2.3.1",
|
||||
|
|
@ -2299,15 +2298,6 @@
|
|||
"url": "https://opencollective.com/vitest"
|
||||
}
|
||||
},
|
||||
"node_modules/@xmldom/xmldom": {
|
||||
"version": "0.8.13",
|
||||
"resolved": "https://registry.npmjs.org/@xmldom/xmldom/-/xmldom-0.8.13.tgz",
|
||||
"integrity": "sha512-KRYzxepc14G/CEpEGc3Yn+JKaAeT63smlDr+vjB8jRfgTBBI9wRj/nkQEO+ucV8p8I9bfKLWp37uHgFrbntPvw==",
|
||||
"license": "MIT",
|
||||
"engines": {
|
||||
"node": ">=10.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/abbrev": {
|
||||
"version": "1.1.1",
|
||||
"resolved": "https://registry.npmjs.org/abbrev/-/abbrev-1.1.1.tgz",
|
||||
|
|
@ -2671,12 +2661,6 @@
|
|||
"node": "*"
|
||||
}
|
||||
},
|
||||
"node_modules/bluebird": {
|
||||
"version": "3.4.7",
|
||||
"resolved": "https://registry.npmjs.org/bluebird/-/bluebird-3.4.7.tgz",
|
||||
"integrity": "sha512-iD3898SR7sWVRHbiQv+sHUtHnMvC1o3nW5rAcqnq3uOn07DSAppZYUkIGslDz6gXC7HfunPe7YVBgoEJASPcHA==",
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/body-parser": {
|
||||
"version": "2.3.0",
|
||||
"resolved": "https://registry.npmjs.org/body-parser/-/body-parser-2.3.0.tgz",
|
||||
|
|
@ -3016,12 +3000,6 @@
|
|||
"url": "https://opencollective.com/core-js"
|
||||
}
|
||||
},
|
||||
"node_modules/core-util-is": {
|
||||
"version": "1.0.3",
|
||||
"resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.3.tgz",
|
||||
"integrity": "sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ==",
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/crelt": {
|
||||
"version": "1.0.7",
|
||||
"resolved": "https://registry.npmjs.org/crelt/-/crelt-1.0.7.tgz",
|
||||
|
|
@ -3250,12 +3228,6 @@
|
|||
"node": ">=0.3.1"
|
||||
}
|
||||
},
|
||||
"node_modules/dingbat-to-unicode": {
|
||||
"version": "1.0.1",
|
||||
"resolved": "https://registry.npmjs.org/dingbat-to-unicode/-/dingbat-to-unicode-1.0.1.tgz",
|
||||
"integrity": "sha512-98l0sW87ZT58pU4i61wa2OHwxbiYSbuxsCBozaVnYX2iCnr3bLM3fIes1/ej7h1YdOKuKt/MLs706TVnALA65w==",
|
||||
"license": "BSD-2-Clause"
|
||||
},
|
||||
"node_modules/doctrine": {
|
||||
"version": "2.1.0",
|
||||
"resolved": "https://registry.npmjs.org/doctrine/-/doctrine-2.1.0.tgz",
|
||||
|
|
@ -3276,15 +3248,6 @@
|
|||
"dev": true,
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/duck": {
|
||||
"version": "0.1.12",
|
||||
"resolved": "https://registry.npmjs.org/duck/-/duck-0.1.12.tgz",
|
||||
"integrity": "sha512-wkctla1O6VfP89gQ+J/yDesM0S7B7XLXjKGzXxMDVFg7uEn706niAtyYovKbyq1oT9YwDcly721/iUWoc8MVRg==",
|
||||
"license": "BSD",
|
||||
"dependencies": {
|
||||
"underscore": "^1.13.1"
|
||||
}
|
||||
},
|
||||
"node_modules/dunder-proto": {
|
||||
"version": "1.0.1",
|
||||
"resolved": "https://registry.npmjs.org/dunder-proto/-/dunder-proto-1.0.1.tgz",
|
||||
|
|
@ -5390,12 +5353,6 @@
|
|||
"node": ">= 4"
|
||||
}
|
||||
},
|
||||
"node_modules/immediate": {
|
||||
"version": "3.0.6",
|
||||
"resolved": "https://registry.npmjs.org/immediate/-/immediate-3.0.6.tgz",
|
||||
"integrity": "sha512-XXOFtyqDjNDAQxVfYxuF7g9Il/IbWmmlQg2MYKOH8ExIT1qg6xc4zyS3HaEEATgs1btfzxq15ciUiY7gjSXRGQ==",
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/import-fresh": {
|
||||
"version": "3.3.1",
|
||||
"resolved": "https://registry.npmjs.org/import-fresh/-/import-fresh-3.3.1.tgz",
|
||||
|
|
@ -6084,18 +6041,6 @@
|
|||
"node": ">=4.0"
|
||||
}
|
||||
},
|
||||
"node_modules/jszip": {
|
||||
"version": "3.10.1",
|
||||
"resolved": "https://registry.npmjs.org/jszip/-/jszip-3.10.1.tgz",
|
||||
"integrity": "sha512-xXDvecyTpGLrqFrvkrUSoxxfJI5AH7U8zxxtVclpsUtMCq4JQ290LY8AW5c7Ggnr/Y/oK+bQMbqK2qmtk3pN4g==",
|
||||
"license": "(MIT OR GPL-3.0-or-later)",
|
||||
"dependencies": {
|
||||
"lie": "~3.3.0",
|
||||
"pako": "~1.0.2",
|
||||
"readable-stream": "~2.3.6",
|
||||
"setimmediate": "^1.0.5"
|
||||
}
|
||||
},
|
||||
"node_modules/jwa": {
|
||||
"version": "2.0.1",
|
||||
"resolved": "https://registry.npmjs.org/jwa/-/jwa-2.0.1.tgz",
|
||||
|
|
@ -6157,15 +6102,6 @@
|
|||
"node": ">= 0.8.0"
|
||||
}
|
||||
},
|
||||
"node_modules/lie": {
|
||||
"version": "3.3.0",
|
||||
"resolved": "https://registry.npmjs.org/lie/-/lie-3.3.0.tgz",
|
||||
"integrity": "sha512-UaiMJzeWRlEujzAuw5LokY1L5ecNQYZKfmyZ9L7wDHb/p5etKaxXhohBcrw0EYby+G/NA52vRSN4N39dxHAIwQ==",
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"immediate": "~3.0.5"
|
||||
}
|
||||
},
|
||||
"node_modules/lightningcss": {
|
||||
"version": "1.32.0",
|
||||
"resolved": "https://registry.npmjs.org/lightningcss/-/lightningcss-1.32.0.tgz",
|
||||
|
|
@ -6488,17 +6424,6 @@
|
|||
"loose-envify": "cli.js"
|
||||
}
|
||||
},
|
||||
"node_modules/lop": {
|
||||
"version": "0.4.2",
|
||||
"resolved": "https://registry.npmjs.org/lop/-/lop-0.4.2.tgz",
|
||||
"integrity": "sha512-RefILVDQ4DKoRZsJ4Pj22TxE3omDO47yFpkIBoDKzkqPRISs5U1cnAdg/5583YPkWPaLIYHOKRMQSvjFsO26cw==",
|
||||
"license": "BSD-2-Clause",
|
||||
"dependencies": {
|
||||
"duck": "^0.1.12",
|
||||
"option": "~0.2.1",
|
||||
"underscore": "^1.13.1"
|
||||
}
|
||||
},
|
||||
"node_modules/lowlight": {
|
||||
"version": "3.3.0",
|
||||
"resolved": "https://registry.npmjs.org/lowlight/-/lowlight-3.3.0.tgz",
|
||||
|
|
@ -6534,39 +6459,6 @@
|
|||
"@jridgewell/sourcemap-codec": "^1.5.5"
|
||||
}
|
||||
},
|
||||
"node_modules/mammoth": {
|
||||
"version": "1.12.0",
|
||||
"resolved": "https://registry.npmjs.org/mammoth/-/mammoth-1.12.0.tgz",
|
||||
"integrity": "sha512-cwnK1RIcRdDMi2HRx2EXGYlxqIEh0Oo3bLhorgnsVJi2UkbX1+jKxuBNR9PC5+JaX7EkmJxFPmo6mjLpqShI2w==",
|
||||
"license": "BSD-2-Clause",
|
||||
"dependencies": {
|
||||
"@xmldom/xmldom": "^0.8.6",
|
||||
"argparse": "~1.0.3",
|
||||
"base64-js": "^1.5.1",
|
||||
"bluebird": "~3.4.0",
|
||||
"dingbat-to-unicode": "^1.0.1",
|
||||
"jszip": "^3.7.1",
|
||||
"lop": "^0.4.2",
|
||||
"path-is-absolute": "^1.0.0",
|
||||
"underscore": "^1.13.1",
|
||||
"xmlbuilder": "^10.0.0"
|
||||
},
|
||||
"bin": {
|
||||
"mammoth": "bin/mammoth"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=12.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/mammoth/node_modules/argparse": {
|
||||
"version": "1.0.10",
|
||||
"resolved": "https://registry.npmjs.org/argparse/-/argparse-1.0.10.tgz",
|
||||
"integrity": "sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg==",
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"sprintf-js": "~1.0.2"
|
||||
}
|
||||
},
|
||||
"node_modules/math-intrinsics": {
|
||||
"version": "1.1.0",
|
||||
"resolved": "https://registry.npmjs.org/math-intrinsics/-/math-intrinsics-1.1.0.tgz",
|
||||
|
|
@ -7137,12 +7029,6 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"node_modules/option": {
|
||||
"version": "0.2.4",
|
||||
"resolved": "https://registry.npmjs.org/option/-/option-0.2.4.tgz",
|
||||
"integrity": "sha512-pkEqbDyl8ou5cpq+VsnQbe/WlEy5qS7xPzMS1U55OCG9KPvwFD46zDbxQIj3egJSFc3D+XhYOPUzz49zQAVy7A==",
|
||||
"license": "BSD-2-Clause"
|
||||
},
|
||||
"node_modules/optionator": {
|
||||
"version": "0.9.4",
|
||||
"resolved": "https://registry.npmjs.org/optionator/-/optionator-0.9.4.tgz",
|
||||
|
|
@ -7224,12 +7110,6 @@
|
|||
"node": ">=8"
|
||||
}
|
||||
},
|
||||
"node_modules/pako": {
|
||||
"version": "1.0.11",
|
||||
"resolved": "https://registry.npmjs.org/pako/-/pako-1.0.11.tgz",
|
||||
"integrity": "sha512-4hLB8Py4zZce5s4yd9XzopqwVv/yGNhV1Bl8NTmCq1763HeK2+EwVTv+leGeL13Dnh2wfbqowVPXCIO0z4taYw==",
|
||||
"license": "(MIT AND Zlib)"
|
||||
},
|
||||
"node_modules/parent-module": {
|
||||
"version": "1.0.1",
|
||||
"resolved": "https://registry.npmjs.org/parent-module/-/parent-module-1.0.1.tgz",
|
||||
|
|
@ -7268,15 +7148,6 @@
|
|||
"node": ">=8"
|
||||
}
|
||||
},
|
||||
"node_modules/path-is-absolute": {
|
||||
"version": "1.0.1",
|
||||
"resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz",
|
||||
"integrity": "sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==",
|
||||
"license": "MIT",
|
||||
"engines": {
|
||||
"node": ">=0.10.0"
|
||||
}
|
||||
},
|
||||
"node_modules/path-key": {
|
||||
"version": "3.1.1",
|
||||
"resolved": "https://registry.npmjs.org/path-key/-/path-key-3.1.1.tgz",
|
||||
|
|
@ -7395,12 +7266,6 @@
|
|||
"node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/process-nextick-args": {
|
||||
"version": "2.0.1",
|
||||
"resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.1.tgz",
|
||||
"integrity": "sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==",
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/prop-types": {
|
||||
"version": "15.8.1",
|
||||
"resolved": "https://registry.npmjs.org/prop-types/-/prop-types-15.8.1.tgz",
|
||||
|
|
@ -7527,33 +7392,6 @@
|
|||
"dev": true,
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/readable-stream": {
|
||||
"version": "2.3.8",
|
||||
"resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.8.tgz",
|
||||
"integrity": "sha512-8p0AUk4XODgIewSi0l8Epjs+EVnWiK7NoDIEGU0HhE7+ZyY8D1IMY7odu5lRrFXGg71L15KG8QrPmum45RTtdA==",
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"core-util-is": "~1.0.0",
|
||||
"inherits": "~2.0.3",
|
||||
"isarray": "~1.0.0",
|
||||
"process-nextick-args": "~2.0.0",
|
||||
"safe-buffer": "~5.1.1",
|
||||
"string_decoder": "~1.1.1",
|
||||
"util-deprecate": "~1.0.1"
|
||||
}
|
||||
},
|
||||
"node_modules/readable-stream/node_modules/isarray": {
|
||||
"version": "1.0.0",
|
||||
"resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz",
|
||||
"integrity": "sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ==",
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/readable-stream/node_modules/safe-buffer": {
|
||||
"version": "5.1.2",
|
||||
"resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz",
|
||||
"integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==",
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/readdirp": {
|
||||
"version": "4.1.2",
|
||||
"resolved": "https://registry.npmjs.org/readdirp/-/readdirp-4.1.2.tgz",
|
||||
|
|
@ -7986,12 +7824,6 @@
|
|||
"node": ">= 0.4"
|
||||
}
|
||||
},
|
||||
"node_modules/setimmediate": {
|
||||
"version": "1.0.5",
|
||||
"resolved": "https://registry.npmjs.org/setimmediate/-/setimmediate-1.0.5.tgz",
|
||||
"integrity": "sha512-MATJdZp8sLqDl/68LfQmbP8zKPLQNV6BIZoIgrscFDQ+RsvK/BxeDQOgyxKKoh0y/8h3BqVFnCqQ/gd+reiIXA==",
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/setprototypeof": {
|
||||
"version": "1.2.0",
|
||||
"resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.2.0.tgz",
|
||||
|
|
@ -8154,12 +7986,6 @@
|
|||
"url": "https://github.com/sponsors/wooorm"
|
||||
}
|
||||
},
|
||||
"node_modules/sprintf-js": {
|
||||
"version": "1.0.3",
|
||||
"resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz",
|
||||
"integrity": "sha512-D9cPgkvLlV3t3IzL0D0YLvGA9Ahk4PcvVwUbN0dSGr1aP0Nrt4AEnTUbuGvquEC0mA64Gqt1fzirlRs5ibXx8g==",
|
||||
"license": "BSD-3-Clause"
|
||||
},
|
||||
"node_modules/stackback": {
|
||||
"version": "0.0.2",
|
||||
"resolved": "https://registry.npmjs.org/stackback/-/stackback-0.0.2.tgz",
|
||||
|
|
@ -8207,21 +8033,6 @@
|
|||
"node": ">= 0.4"
|
||||
}
|
||||
},
|
||||
"node_modules/string_decoder": {
|
||||
"version": "1.1.1",
|
||||
"resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz",
|
||||
"integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==",
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"safe-buffer": "~5.1.0"
|
||||
}
|
||||
},
|
||||
"node_modules/string_decoder/node_modules/safe-buffer": {
|
||||
"version": "5.1.2",
|
||||
"resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz",
|
||||
"integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==",
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/string.prototype.matchall": {
|
||||
"version": "4.0.12",
|
||||
"resolved": "https://registry.npmjs.org/string.prototype.matchall/-/string.prototype.matchall-4.0.12.tgz",
|
||||
|
|
@ -8872,12 +8683,6 @@
|
|||
"url": "https://github.com/sponsors/ljharb"
|
||||
}
|
||||
},
|
||||
"node_modules/underscore": {
|
||||
"version": "1.13.8",
|
||||
"resolved": "https://registry.npmjs.org/underscore/-/underscore-1.13.8.tgz",
|
||||
"integrity": "sha512-DXtD3ZtEQzc7M8m4cXotyHR+FAS18C64asBYY5vqZexfYryNNnDc02W4hKg3rdQuqOYas1jkseX0+nZXjTXnvQ==",
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/undici-types": {
|
||||
"version": "8.3.0",
|
||||
"resolved": "https://registry.npmjs.org/undici-types/-/undici-types-8.3.0.tgz",
|
||||
|
|
@ -8990,12 +8795,6 @@
|
|||
"punycode": "^2.1.0"
|
||||
}
|
||||
},
|
||||
"node_modules/util-deprecate": {
|
||||
"version": "1.0.2",
|
||||
"resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz",
|
||||
"integrity": "sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==",
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/uuid": {
|
||||
"version": "14.0.1",
|
||||
"resolved": "https://registry.npmjs.org/uuid/-/uuid-14.0.1.tgz",
|
||||
|
|
@ -9400,15 +9199,6 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"node_modules/xmlbuilder": {
|
||||
"version": "10.1.1",
|
||||
"resolved": "https://registry.npmjs.org/xmlbuilder/-/xmlbuilder-10.1.1.tgz",
|
||||
"integrity": "sha512-OyzrcFLL/nb6fMGHbiRDuPup9ljBycsdCypwuyg5AAHvyWzGfChJpCXMG88AGTIMFhGZ9RccFN1e6lhg3hkwKg==",
|
||||
"license": "MIT",
|
||||
"engines": {
|
||||
"node": ">=4.0"
|
||||
}
|
||||
},
|
||||
"node_modules/yaml": {
|
||||
"version": "2.9.0",
|
||||
"resolved": "https://registry.npmjs.org/yaml/-/yaml-2.9.0.tgz",
|
||||
|
|
|
|||
|
|
@ -57,7 +57,6 @@
|
|||
"highlight.js": "^11.11.1",
|
||||
"katex": "^0.17.0",
|
||||
"lowlight": "^3.3.0",
|
||||
"mammoth": "^1.12.0",
|
||||
"openai": "^6.45.0",
|
||||
"path-browserify": "^1.0.1",
|
||||
"regex-parser": "^2.3.1",
|
||||
|
|
|
|||
Loading…
Reference in a new issue