@usejunior/docx-mcp 0.3.1 → 0.6.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/dist/.tsbuildinfo +1 -1
- package/dist/cli/commands/grep.d.ts +15 -0
- package/dist/cli/commands/grep.d.ts.map +1 -0
- package/dist/cli/commands/grep.js +128 -0
- package/dist/cli/commands/grep.js.map +1 -0
- package/dist/cli/flag_parser.js +1 -1
- package/dist/cli/flag_parser.js.map +1 -1
- package/dist/cli/help.d.ts.map +1 -1
- package/dist/cli/help.js +1 -0
- package/dist/cli/help.js.map +1 -1
- package/dist/cli/index.d.ts.map +1 -1
- package/dist/cli/index.js +7 -0
- package/dist/cli/index.js.map +1 -1
- package/dist/conformance/harness.d.ts.map +1 -1
- package/dist/conformance/harness.js +10 -11
- package/dist/conformance/harness.js.map +1 -1
- package/dist/gdocs_loader.d.ts +2 -0
- package/dist/gdocs_loader.d.ts.map +1 -0
- package/dist/gdocs_loader.js +14 -0
- package/dist/gdocs_loader.js.map +1 -0
- package/dist/server.d.ts +2 -2
- package/dist/server.d.ts.map +1 -1
- package/dist/server.js +68 -7
- package/dist/server.js.map +1 -1
- package/dist/session/manager.d.ts +52 -16
- package/dist/session/manager.d.ts.map +1 -1
- package/dist/session/manager.js +140 -56
- package/dist/session/manager.js.map +1 -1
- package/dist/tool_catalog.d.ts +44 -55
- package/dist/tool_catalog.d.ts.map +1 -1
- package/dist/tool_catalog.js +56 -41
- package/dist/tool_catalog.js.map +1 -1
- package/dist/tools/accept_changes.d.ts +0 -1
- package/dist/tools/accept_changes.d.ts.map +1 -1
- package/dist/tools/accept_changes.js +1 -1
- package/dist/tools/accept_changes.js.map +1 -1
- package/dist/tools/add_comment.d.ts +0 -1
- package/dist/tools/add_comment.d.ts.map +1 -1
- package/dist/tools/add_comment.js +2 -2
- package/dist/tools/add_comment.js.map +1 -1
- package/dist/tools/add_footnote.d.ts +0 -1
- package/dist/tools/add_footnote.d.ts.map +1 -1
- package/dist/tools/add_footnote.js +1 -1
- package/dist/tools/add_footnote.js.map +1 -1
- package/dist/tools/apply_plan.d.ts +0 -1
- package/dist/tools/apply_plan.d.ts.map +1 -1
- package/dist/tools/apply_plan.js +6 -6
- package/dist/tools/apply_plan.js.map +1 -1
- package/dist/tools/clear_formatting.d.ts +0 -1
- package/dist/tools/clear_formatting.d.ts.map +1 -1
- package/dist/tools/clear_formatting.js +1 -1
- package/dist/tools/clear_formatting.js.map +1 -1
- package/dist/tools/{clear_session.d.ts → close_file.d.ts} +2 -3
- package/dist/tools/close_file.d.ts.map +1 -0
- package/dist/tools/close_file.js +46 -0
- package/dist/tools/close_file.js.map +1 -0
- package/dist/tools/compare_documents.d.ts +0 -1
- package/dist/tools/compare_documents.d.ts.map +1 -1
- package/dist/tools/compare_documents.js +4 -5
- package/dist/tools/compare_documents.js.map +1 -1
- package/dist/tools/delete_comment.d.ts +0 -1
- package/dist/tools/delete_comment.d.ts.map +1 -1
- package/dist/tools/delete_comment.js +1 -1
- package/dist/tools/delete_comment.js.map +1 -1
- package/dist/tools/delete_footnote.d.ts +0 -1
- package/dist/tools/delete_footnote.d.ts.map +1 -1
- package/dist/tools/delete_footnote.js +1 -1
- package/dist/tools/delete_footnote.js.map +1 -1
- package/dist/tools/extract_revisions.d.ts +0 -1
- package/dist/tools/extract_revisions.d.ts.map +1 -1
- package/dist/tools/extract_revisions.js +1 -1
- package/dist/tools/extract_revisions.js.map +1 -1
- package/dist/tools/format_layout.d.ts +0 -1
- package/dist/tools/format_layout.d.ts.map +1 -1
- package/dist/tools/format_layout.js +1 -1
- package/dist/tools/format_layout.js.map +1 -1
- package/dist/tools/gdocs/close_file.d.ts +4 -0
- package/dist/tools/gdocs/close_file.d.ts.map +1 -0
- package/dist/tools/gdocs/close_file.js +15 -0
- package/dist/tools/gdocs/close_file.js.map +1 -0
- package/dist/tools/gdocs/format_layout.d.ts +14 -0
- package/dist/tools/gdocs/format_layout.d.ts.map +1 -0
- package/dist/tools/gdocs/format_layout.js +88 -0
- package/dist/tools/gdocs/format_layout.js.map +1 -0
- package/dist/tools/gdocs/get_file_status.d.ts +4 -0
- package/dist/tools/gdocs/get_file_status.d.ts.map +1 -0
- package/dist/tools/gdocs/get_file_status.js +22 -0
- package/dist/tools/gdocs/get_file_status.js.map +1 -0
- package/dist/tools/gdocs/grep.d.ts +13 -0
- package/dist/tools/gdocs/grep.d.ts.map +1 -0
- package/dist/tools/gdocs/grep.js +113 -0
- package/dist/tools/gdocs/grep.js.map +1 -0
- package/dist/tools/gdocs/insert_paragraph.d.ts +9 -0
- package/dist/tools/gdocs/insert_paragraph.d.ts.map +1 -0
- package/dist/tools/gdocs/insert_paragraph.js +35 -0
- package/dist/tools/gdocs/insert_paragraph.js.map +1 -0
- package/dist/tools/gdocs/read_file.d.ts +9 -0
- package/dist/tools/gdocs/read_file.d.ts.map +1 -0
- package/dist/tools/gdocs/read_file.js +116 -0
- package/dist/tools/gdocs/read_file.js.map +1 -0
- package/dist/tools/gdocs/replace_text.d.ts +9 -0
- package/dist/tools/gdocs/replace_text.d.ts.map +1 -0
- package/dist/tools/gdocs/replace_text.js +35 -0
- package/dist/tools/gdocs/replace_text.js.map +1 -0
- package/dist/tools/gdocs/save.d.ts +7 -0
- package/dist/tools/gdocs/save.d.ts.map +1 -0
- package/dist/tools/gdocs/save.js +46 -0
- package/dist/tools/gdocs/save.js.map +1 -0
- package/dist/tools/get_comments.d.ts +0 -1
- package/dist/tools/get_comments.d.ts.map +1 -1
- package/dist/tools/get_comments.js +1 -1
- package/dist/tools/get_comments.js.map +1 -1
- package/dist/tools/get_file_status.d.ts +6 -0
- package/dist/tools/get_file_status.d.ts.map +1 -0
- package/dist/tools/get_file_status.js +40 -0
- package/dist/tools/get_file_status.js.map +1 -0
- package/dist/tools/get_footnotes.d.ts +0 -1
- package/dist/tools/get_footnotes.d.ts.map +1 -1
- package/dist/tools/get_footnotes.js +1 -1
- package/dist/tools/get_footnotes.js.map +1 -1
- package/dist/tools/grep.d.ts +5 -2
- package/dist/tools/grep.d.ts.map +1 -1
- package/dist/tools/grep.js +236 -90
- package/dist/tools/grep.js.map +1 -1
- package/dist/tools/has_tracked_changes.d.ts +0 -1
- package/dist/tools/has_tracked_changes.d.ts.map +1 -1
- package/dist/tools/has_tracked_changes.js +1 -1
- package/dist/tools/has_tracked_changes.js.map +1 -1
- package/dist/tools/init_plan.d.ts +0 -1
- package/dist/tools/init_plan.d.ts.map +1 -1
- package/dist/tools/init_plan.js +2 -1
- package/dist/tools/init_plan.js.map +1 -1
- package/dist/tools/insert_paragraph.d.ts +0 -1
- package/dist/tools/insert_paragraph.d.ts.map +1 -1
- package/dist/tools/insert_paragraph.js +1 -1
- package/dist/tools/insert_paragraph.js.map +1 -1
- package/dist/tools/open_document.d.ts.map +1 -1
- package/dist/tools/open_document.js +1 -2
- package/dist/tools/open_document.js.map +1 -1
- package/dist/tools/provider_guard.d.ts +3 -0
- package/dist/tools/provider_guard.d.ts.map +1 -0
- package/dist/tools/provider_guard.js +12 -0
- package/dist/tools/provider_guard.js.map +1 -0
- package/dist/tools/read_file.d.ts +0 -1
- package/dist/tools/read_file.d.ts.map +1 -1
- package/dist/tools/read_file.js +89 -17
- package/dist/tools/read_file.js.map +1 -1
- package/dist/tools/replace_text.d.ts +0 -1
- package/dist/tools/replace_text.d.ts.map +1 -1
- package/dist/tools/replace_text.js +1 -1
- package/dist/tools/replace_text.js.map +1 -1
- package/dist/tools/save.d.ts +0 -1
- package/dist/tools/save.d.ts.map +1 -1
- package/dist/tools/save.js +3 -4
- package/dist/tools/save.js.map +1 -1
- package/dist/tools/session_resolution.d.ts +16 -4
- package/dist/tools/session_resolution.d.ts.map +1 -1
- package/dist/tools/session_resolution.js +132 -67
- package/dist/tools/session_resolution.js.map +1 -1
- package/dist/tools/update_footnote.d.ts +0 -1
- package/dist/tools/update_footnote.d.ts.map +1 -1
- package/dist/tools/update_footnote.js +1 -1
- package/dist/tools/update_footnote.js.map +1 -1
- package/package.json +11 -3
- package/dist/tools/clear_session.d.ts.map +0 -1
- package/dist/tools/clear_session.js +0 -66
- package/dist/tools/clear_session.js.map +0 -1
package/dist/server.js
CHANGED
|
@@ -11,9 +11,9 @@ import { insertParagraph } from './tools/insert_paragraph.js';
|
|
|
11
11
|
import { mergePlans } from './tools/merge_plans.js';
|
|
12
12
|
import { applyPlan } from './tools/apply_plan.js';
|
|
13
13
|
import { save } from './tools/save.js';
|
|
14
|
-
import {
|
|
14
|
+
import { getFileStatus } from './tools/get_file_status.js';
|
|
15
15
|
import { hasTrackedChanges_tool } from './tools/has_tracked_changes.js';
|
|
16
|
-
import {
|
|
16
|
+
import { closeFile } from './tools/close_file.js';
|
|
17
17
|
import { formatLayout } from './tools/format_layout.js';
|
|
18
18
|
import { acceptChanges } from './tools/accept_changes.js';
|
|
19
19
|
import { addComment } from './tools/add_comment.js';
|
|
@@ -26,13 +26,62 @@ import { deleteFootnote } from './tools/delete_footnote.js';
|
|
|
26
26
|
import { compareDocuments_tool } from './tools/compare_documents.js';
|
|
27
27
|
import { extractRevisions_tool } from './tools/extract_revisions.js';
|
|
28
28
|
import { clearFormatting } from './tools/clear_formatting.js';
|
|
29
|
+
import { resolveGDocsSessionForTool } from './tools/session_resolution.js';
|
|
30
|
+
import { checkGDocsSupport } from './tools/provider_guard.js';
|
|
29
31
|
export const MCP_TRANSPORT = 'stdio';
|
|
30
32
|
export const MCP_TOOLS = SAFE_DOCX_MCP_TOOLS;
|
|
33
|
+
function isGDocsRequest(args) {
|
|
34
|
+
return typeof args.google_doc_id === 'string' && args.google_doc_id.trim().length > 0;
|
|
35
|
+
}
|
|
36
|
+
// Lazy-loaded gdocs handler map (populated on first gdocs request)
|
|
37
|
+
let gdocsHandlers = null;
|
|
38
|
+
async function loadGDocsHandlers() {
|
|
39
|
+
if (gdocsHandlers)
|
|
40
|
+
return gdocsHandlers;
|
|
41
|
+
const [readFile, replaceText, insertParagraph, grep, save, formatLayout, getFileStatus, closeFile] = await Promise.all([
|
|
42
|
+
import('./tools/gdocs/read_file.js'),
|
|
43
|
+
import('./tools/gdocs/replace_text.js'),
|
|
44
|
+
import('./tools/gdocs/insert_paragraph.js'),
|
|
45
|
+
import('./tools/gdocs/grep.js'),
|
|
46
|
+
import('./tools/gdocs/save.js'),
|
|
47
|
+
import('./tools/gdocs/format_layout.js'),
|
|
48
|
+
import('./tools/gdocs/get_file_status.js'),
|
|
49
|
+
import('./tools/gdocs/close_file.js'),
|
|
50
|
+
]);
|
|
51
|
+
gdocsHandlers = {
|
|
52
|
+
read_file: readFile.gdocsReadFile,
|
|
53
|
+
replace_text: replaceText.gdocsReplaceText,
|
|
54
|
+
insert_paragraph: insertParagraph.gdocsInsertParagraph,
|
|
55
|
+
grep: grep.gdocsGrep,
|
|
56
|
+
save: save.gdocsSave,
|
|
57
|
+
format_layout: formatLayout.gdocsFormatLayout,
|
|
58
|
+
get_file_status: getFileStatus.gdocsGetFileStatus,
|
|
59
|
+
close_file: closeFile.gdocsCloseFile,
|
|
60
|
+
};
|
|
61
|
+
return gdocsHandlers;
|
|
62
|
+
}
|
|
63
|
+
async function dispatchGDocs(manager, args, toolName) {
|
|
64
|
+
const guard = checkGDocsSupport(toolName);
|
|
65
|
+
if (guard)
|
|
66
|
+
return guard;
|
|
67
|
+
const resolved = await resolveGDocsSessionForTool(manager, args, { toolName });
|
|
68
|
+
if (!resolved.ok)
|
|
69
|
+
return resolved.response;
|
|
70
|
+
const handlers = await loadGDocsHandlers();
|
|
71
|
+
const handler = handlers[toolName];
|
|
72
|
+
if (!handler)
|
|
73
|
+
return { success: false, error: { code: 'UNKNOWN_TOOL', message: `No Google Docs handler for: ${toolName}` } };
|
|
74
|
+
return handler(manager, resolved.session, args, resolved.metadata);
|
|
75
|
+
}
|
|
31
76
|
export async function dispatchToolCall(sessions, name, args) {
|
|
32
77
|
switch (name) {
|
|
33
78
|
case 'read_file':
|
|
79
|
+
if (isGDocsRequest(args))
|
|
80
|
+
return await dispatchGDocs(sessions, args, 'read_file');
|
|
34
81
|
return await readFile(sessions, args);
|
|
35
82
|
case 'grep':
|
|
83
|
+
if (isGDocsRequest(args))
|
|
84
|
+
return await dispatchGDocs(sessions, args, 'grep');
|
|
36
85
|
return await grep(sessions, args);
|
|
37
86
|
case 'init_plan':
|
|
38
87
|
return await initPlan(sessions, args);
|
|
@@ -41,21 +90,33 @@ export async function dispatchToolCall(sessions, name, args) {
|
|
|
41
90
|
case 'apply_plan':
|
|
42
91
|
return await applyPlan(sessions, args);
|
|
43
92
|
case 'replace_text':
|
|
93
|
+
if (isGDocsRequest(args))
|
|
94
|
+
return await dispatchGDocs(sessions, args, 'replace_text');
|
|
44
95
|
return await replaceText(sessions, args);
|
|
45
96
|
case 'insert_paragraph':
|
|
97
|
+
if (isGDocsRequest(args))
|
|
98
|
+
return await dispatchGDocs(sessions, args, 'insert_paragraph');
|
|
46
99
|
return await insertParagraph(sessions, args);
|
|
47
100
|
case 'save':
|
|
101
|
+
if (isGDocsRequest(args))
|
|
102
|
+
return await dispatchGDocs(sessions, args, 'save');
|
|
48
103
|
return await save(sessions, args);
|
|
49
104
|
case 'format_layout':
|
|
105
|
+
if (isGDocsRequest(args))
|
|
106
|
+
return await dispatchGDocs(sessions, args, 'format_layout');
|
|
50
107
|
return await formatLayout(sessions, args);
|
|
51
108
|
case 'accept_changes':
|
|
52
109
|
return await acceptChanges(sessions, args);
|
|
53
110
|
case 'has_tracked_changes':
|
|
54
111
|
return await hasTrackedChanges_tool(sessions, args);
|
|
55
|
-
case '
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
return await
|
|
112
|
+
case 'get_file_status':
|
|
113
|
+
if (isGDocsRequest(args))
|
|
114
|
+
return await dispatchGDocs(sessions, args, 'get_file_status');
|
|
115
|
+
return await getFileStatus(sessions, args);
|
|
116
|
+
case 'close_file':
|
|
117
|
+
if (isGDocsRequest(args))
|
|
118
|
+
return await dispatchGDocs(sessions, args, 'close_file');
|
|
119
|
+
return await closeFile(sessions, args);
|
|
59
120
|
case 'add_comment':
|
|
60
121
|
return await addComment(sessions, args);
|
|
61
122
|
case 'get_comments':
|
|
@@ -82,7 +143,7 @@ export async function dispatchToolCall(sessions, name, args) {
|
|
|
82
143
|
error: {
|
|
83
144
|
code: 'UNKNOWN_TOOL',
|
|
84
145
|
message: `Unknown tool: ${name}`,
|
|
85
|
-
hint: 'Use file-first tools: read_file, grep, replace_text, insert_paragraph, save,
|
|
146
|
+
hint: 'Use file-first tools: read_file, grep, replace_text, insert_paragraph, save, get_file_status.',
|
|
86
147
|
},
|
|
87
148
|
};
|
|
88
149
|
}
|
package/dist/server.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"server.js","sourceRoot":"","sources":["../src/server.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAE,MAAM,2CAA2C,CAAC;AACnE,OAAO,EAAE,oBAAoB,EAAE,MAAM,2CAA2C,CAAC;AACjF,OAAO,EAAE,qBAAqB,EAAE,sBAAsB,EAAE,MAAM,oCAAoC,CAAC;AAEnG,OAAO,EAAE,cAAc,
|
|
1
|
+
{"version":3,"file":"server.js","sourceRoot":"","sources":["../src/server.ts"],"names":[],"mappings":"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"}
|
|
@@ -26,7 +26,8 @@ export type ExtractionCacheEntry = {
|
|
|
26
26
|
revision: number;
|
|
27
27
|
changes: ParagraphRevision[];
|
|
28
28
|
};
|
|
29
|
-
export type
|
|
29
|
+
export type DocxSession = {
|
|
30
|
+
provider: 'docx';
|
|
30
31
|
sessionId: string;
|
|
31
32
|
filename: string;
|
|
32
33
|
tmpPath: string;
|
|
@@ -35,12 +36,13 @@ export type Session = {
|
|
|
35
36
|
/**
|
|
36
37
|
* Post-normalization + bookmark-cleaned buffer used as comparison baseline for tracked output.
|
|
37
38
|
* Comparing against this instead of originalBuffer prevents normalization artifacts from
|
|
38
|
-
* appearing as false tracked changes.
|
|
39
|
+
* appearing as false tracked changes. Lazily generated on first save/compare via ensureBaselines().
|
|
39
40
|
*/
|
|
40
41
|
comparisonBaseline: Buffer | null;
|
|
41
42
|
/**
|
|
42
43
|
* Post-normalization buffer WITH bookmarks, used as comparison baseline for
|
|
43
44
|
* compare_documents tool (which uses cleanBookmarks: false).
|
|
45
|
+
* Lazily generated on first save/compare via ensureBaselines().
|
|
44
46
|
*/
|
|
45
47
|
comparisonBaselineWithBookmarks: Buffer | null;
|
|
46
48
|
doc: DocxDocument;
|
|
@@ -53,45 +55,79 @@ export type Session = {
|
|
|
53
55
|
expiresAt: Date;
|
|
54
56
|
normalizationStats: NormalizationResult | null;
|
|
55
57
|
};
|
|
58
|
+
export type GDocsSession = {
|
|
59
|
+
provider: 'gdocs';
|
|
60
|
+
sessionId: string;
|
|
61
|
+
docId: string;
|
|
62
|
+
doc: any;
|
|
63
|
+
editCount: number;
|
|
64
|
+
editRevision: number;
|
|
65
|
+
createdAt: Date;
|
|
66
|
+
lastAccessedAt: Date;
|
|
67
|
+
expiresAt: Date;
|
|
68
|
+
};
|
|
69
|
+
export type Session = DocxSession | GDocsSession;
|
|
70
|
+
export declare function isDocxSession(s: Session): s is DocxSession;
|
|
71
|
+
export declare function isGDocsSession(s: Session): s is GDocsSession;
|
|
56
72
|
export declare class SessionManager {
|
|
73
|
+
/** Sessions keyed by canonical file path (realpath). */
|
|
57
74
|
private sessions;
|
|
58
75
|
private ttlMs;
|
|
59
|
-
|
|
76
|
+
/** Concurrency guard: prevents double-generation of baselines for the same session. */
|
|
77
|
+
private baselinePromises;
|
|
60
78
|
constructor(opts?: {
|
|
61
79
|
ttlMs?: number;
|
|
62
80
|
});
|
|
63
81
|
private expandPath;
|
|
64
82
|
normalizePath(inputPath: string): string;
|
|
83
|
+
/** Canonicalize path using realpath (resolves symlinks, case). */
|
|
84
|
+
canonicalizePath(inputPath: string): Promise<string>;
|
|
65
85
|
private newSessionId;
|
|
66
|
-
createSession(documentContent: Buffer, filename: string, originalPath: string): Promise<
|
|
86
|
+
createSession(documentContent: Buffer, filename: string, originalPath: string): Promise<DocxSession>;
|
|
67
87
|
/**
|
|
68
|
-
* Finalize a newly created session by normalizing the document
|
|
69
|
-
* paragraph bookmarks
|
|
88
|
+
* Finalize a newly created session by normalizing the document and inserting
|
|
89
|
+
* paragraph bookmarks. Baselines are lazily generated on first save/compare.
|
|
70
90
|
*
|
|
71
91
|
* INVARIANT: All production session creation paths must call
|
|
72
92
|
* `finalizeNewSession` before returning a session. `createSession` alone
|
|
73
93
|
* leaves baselines null and is incomplete for tool use.
|
|
74
94
|
*/
|
|
75
|
-
finalizeNewSession(session:
|
|
95
|
+
finalizeNewSession(session: DocxSession, opts?: {
|
|
76
96
|
skipNormalization?: boolean;
|
|
77
97
|
}): Promise<{
|
|
78
98
|
normalizationStats: NormalizationResult | null;
|
|
79
99
|
paragraphCount: number;
|
|
80
100
|
}>;
|
|
101
|
+
/**
|
|
102
|
+
* Lazily generate comparison baselines from the immutable originalBuffer.
|
|
103
|
+
* Safe to call multiple times — returns immediately if baselines already exist.
|
|
104
|
+
* Uses a concurrency guard to prevent double-generation from parallel calls.
|
|
105
|
+
*/
|
|
106
|
+
ensureBaselines(session: DocxSession): Promise<void>;
|
|
107
|
+
private _generateBaselines;
|
|
108
|
+
/** Get session by file path (auto-canonicalizes). */
|
|
109
|
+
getSessionByFilePath(filePath: string): Promise<Session | null>;
|
|
110
|
+
/** Get session by canonical file path. Returns null if not found or expired. */
|
|
111
|
+
getSessionByPath(canonicalPath: string): Session | null;
|
|
112
|
+
/**
|
|
113
|
+
* @deprecated Use getSessionByPath instead. Kept only for backward compatibility during migration.
|
|
114
|
+
*/
|
|
81
115
|
getSession(sessionId: string): Session;
|
|
82
|
-
private listActiveSessionsForPath;
|
|
83
|
-
getMostRecentlyUsedSessionForPath(normalizedPath: string): Session | null;
|
|
84
116
|
private cleanupSessionArtifacts;
|
|
85
|
-
|
|
86
|
-
clearSessionsByPath(normalizedPath: string): Promise<string[]>;
|
|
117
|
+
clearSessionByPath(filePath: string): Promise<string | null>;
|
|
87
118
|
clearAllSessions(): Promise<string[]>;
|
|
88
119
|
touch(session: Session): void;
|
|
89
120
|
markEdited(session: Session): void;
|
|
90
|
-
getSaveCache(session:
|
|
91
|
-
setSaveCache(session:
|
|
92
|
-
getExtractionCache(session:
|
|
93
|
-
setExtractionCache(session:
|
|
94
|
-
|
|
121
|
+
getSaveCache(session: DocxSession, cacheKey: string): SaveCacheEntry | null;
|
|
122
|
+
setSaveCache(session: DocxSession, entry: SaveCacheEntry): void;
|
|
123
|
+
getExtractionCache(session: DocxSession): ExtractionCacheEntry | null;
|
|
124
|
+
setExtractionCache(session: DocxSession, changes: ParagraphRevision[]): void;
|
|
125
|
+
/**
|
|
126
|
+
* Create a Google Docs session. The `doc` is an already-loaded
|
|
127
|
+
* GoogleDocsDocument instance (created via dynamic import in the handler layer).
|
|
128
|
+
*/
|
|
129
|
+
createGDocsSession(docId: string, doc: any): GDocsSession;
|
|
130
|
+
saveTo(session: DocxSession, savePath: string, opts?: {
|
|
95
131
|
cleanBookmarks?: boolean;
|
|
96
132
|
}): Promise<void>;
|
|
97
133
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"manager.d.ts","sourceRoot":"","sources":["../../src/session/manager.ts"],"names":[],"mappings":"AAIA,OAAO,EACL,YAAY,EACZ,KAAK,mBAAmB,EACxB,KAAK,iBAAiB,EACtB,KAAK,kBAAkB,EACvB,KAAK,4BAA4B,EACjC,KAAK,iCAAiC,EACvC,MAAM,sBAAsB,CAAC;AAE9B,MAAM,MAAM,UAAU,GAAG,OAAO,GAAG,SAAS,GAAG,MAAM,CAAC;AAEtD,MAAM,MAAM,mBAAmB,GAAG;IAChC,UAAU,EAAE,MAAM,CAAC;IACnB,SAAS,EAAE,MAAM,CAAC;IAClB,aAAa,EAAE,MAAM,CAAC;CACvB,CAAC;AAEF,MAAM,MAAM,cAAc,GAAG;IAC3B,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,MAAM,CAAC;IACjB,MAAM,EAAE,UAAU,CAAC;IACnB,cAAc,EAAE,OAAO,CAAC;IACxB,aAAa,EAAE,MAAM,GAAG,UAAU,CAAC;IACnC,aAAa,EAAE,MAAM,CAAC;IACtB,aAAa,EAAE,MAAM,CAAC;IACtB,aAAa,EAAE,MAAM,GAAG,IAAI,CAAC;IAC7B,YAAY,EAAE,mBAAmB,GAAG,IAAI,CAAC;IACzC,yBAAyB,CAAC,EAAE,kBAAkB,CAAC;IAC/C,qBAAqB,CAAC,EAAE,4BAA4B,CAAC;IACrD,0BAA0B,CAAC,EAAE,iCAAiC,CAAC;IAC/D,gBAAgB,EAAE,MAAM,CAAC;IACzB,aAAa,EAAE,MAAM,CAAC;IACtB,WAAW,EAAE,MAAM,CAAC;CACrB,CAAC;AAEF,MAAM,MAAM,oBAAoB,GAAG;IACjC,QAAQ,EAAE,MAAM,CAAC;IACjB,OAAO,EAAE,iBAAiB,EAAE,CAAC;CAC9B,CAAC;AAEF,MAAM,MAAM,
|
|
1
|
+
{"version":3,"file":"manager.d.ts","sourceRoot":"","sources":["../../src/session/manager.ts"],"names":[],"mappings":"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"}
|
package/dist/session/manager.js
CHANGED
|
@@ -3,10 +3,18 @@ import path from 'node:path';
|
|
|
3
3
|
import os from 'node:os';
|
|
4
4
|
import fs from 'node:fs/promises';
|
|
5
5
|
import { DocxDocument, } from '@usejunior/docx-core';
|
|
6
|
+
export function isDocxSession(s) {
|
|
7
|
+
return s.provider === 'docx';
|
|
8
|
+
}
|
|
9
|
+
export function isGDocsSession(s) {
|
|
10
|
+
return s.provider === 'gdocs';
|
|
11
|
+
}
|
|
6
12
|
export class SessionManager {
|
|
13
|
+
/** Sessions keyed by canonical file path (realpath). */
|
|
7
14
|
sessions = new Map();
|
|
8
15
|
ttlMs;
|
|
9
|
-
|
|
16
|
+
/** Concurrency guard: prevents double-generation of baselines for the same session. */
|
|
17
|
+
baselinePromises = new WeakMap();
|
|
10
18
|
constructor(opts) {
|
|
11
19
|
this.ttlMs = opts?.ttlMs ?? 60 * 60 * 1000;
|
|
12
20
|
}
|
|
@@ -18,8 +26,18 @@ export class SessionManager {
|
|
|
18
26
|
normalizePath(inputPath) {
|
|
19
27
|
return path.resolve(this.expandPath(inputPath));
|
|
20
28
|
}
|
|
29
|
+
/** Canonicalize path using realpath (resolves symlinks, case). */
|
|
30
|
+
async canonicalizePath(inputPath) {
|
|
31
|
+
const normalized = this.normalizePath(inputPath);
|
|
32
|
+
try {
|
|
33
|
+
return await fs.realpath(normalized);
|
|
34
|
+
}
|
|
35
|
+
catch {
|
|
36
|
+
return normalized;
|
|
37
|
+
}
|
|
38
|
+
}
|
|
21
39
|
newSessionId() {
|
|
22
|
-
// Format: ses_[12 alphanumeric]
|
|
40
|
+
// Format: ses_[12 alphanumeric] — kept for temp dir naming only.
|
|
23
41
|
const alphabet = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789';
|
|
24
42
|
const bytes = randomBytes(12);
|
|
25
43
|
let out = '';
|
|
@@ -29,6 +47,12 @@ export class SessionManager {
|
|
|
29
47
|
return `ses_${out}`;
|
|
30
48
|
}
|
|
31
49
|
async createSession(documentContent, filename, originalPath) {
|
|
50
|
+
const canonicalPath = await this.canonicalizePath(originalPath);
|
|
51
|
+
// One-session-per-file: clean up existing session for this path if any
|
|
52
|
+
const existing = this.sessions.get(canonicalPath);
|
|
53
|
+
if (existing) {
|
|
54
|
+
await this.cleanupSessionArtifacts(existing);
|
|
55
|
+
}
|
|
32
56
|
const sessionId = this.newSessionId();
|
|
33
57
|
const dir = await fs.mkdtemp(path.join(os.tmpdir(), 'safe-docx-'));
|
|
34
58
|
const tmpPath = path.join(dir, filename);
|
|
@@ -38,6 +62,7 @@ export class SessionManager {
|
|
|
38
62
|
const now = new Date();
|
|
39
63
|
const expiresAt = new Date(now.getTime() + this.ttlMs);
|
|
40
64
|
const session = {
|
|
65
|
+
provider: 'docx',
|
|
41
66
|
sessionId,
|
|
42
67
|
filename,
|
|
43
68
|
tmpPath,
|
|
@@ -55,12 +80,12 @@ export class SessionManager {
|
|
|
55
80
|
expiresAt,
|
|
56
81
|
normalizationStats: null,
|
|
57
82
|
};
|
|
58
|
-
this.sessions.set(
|
|
83
|
+
this.sessions.set(canonicalPath, session);
|
|
59
84
|
return session;
|
|
60
85
|
}
|
|
61
86
|
/**
|
|
62
|
-
* Finalize a newly created session by normalizing the document
|
|
63
|
-
* paragraph bookmarks
|
|
87
|
+
* Finalize a newly created session by normalizing the document and inserting
|
|
88
|
+
* paragraph bookmarks. Baselines are lazily generated on first save/compare.
|
|
64
89
|
*
|
|
65
90
|
* INVARIANT: All production session creation paths must call
|
|
66
91
|
* `finalizeNewSession` before returning a session. `createSession` alone
|
|
@@ -71,72 +96,102 @@ export class SessionManager {
|
|
|
71
96
|
session.normalizationStats = session.doc.normalize();
|
|
72
97
|
}
|
|
73
98
|
const info = session.doc.insertParagraphBookmarks(`mcp_${session.sessionId}`);
|
|
74
|
-
|
|
75
|
-
session.doc.toBuffer({ cleanBookmarks: true }),
|
|
76
|
-
session.doc.toBuffer({ cleanBookmarks: false }),
|
|
77
|
-
]);
|
|
78
|
-
session.comparisonBaseline = cleanBaseline.buffer;
|
|
79
|
-
session.comparisonBaselineWithBookmarks = bookmarkedBaseline.buffer;
|
|
99
|
+
// Baselines are lazily generated — skip the two toBuffer() calls here
|
|
80
100
|
this.touch(session);
|
|
81
101
|
return { normalizationStats: session.normalizationStats, paragraphCount: info.paragraphCount };
|
|
82
102
|
}
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
103
|
+
/**
|
|
104
|
+
* Lazily generate comparison baselines from the immutable originalBuffer.
|
|
105
|
+
* Safe to call multiple times — returns immediately if baselines already exist.
|
|
106
|
+
* Uses a concurrency guard to prevent double-generation from parallel calls.
|
|
107
|
+
*/
|
|
108
|
+
async ensureBaselines(session) {
|
|
109
|
+
if (session.comparisonBaseline !== null)
|
|
110
|
+
return;
|
|
111
|
+
const existing = this.baselinePromises.get(session);
|
|
112
|
+
if (existing)
|
|
113
|
+
return existing;
|
|
114
|
+
const promise = this._generateBaselines(session);
|
|
115
|
+
this.baselinePromises.set(session, promise);
|
|
116
|
+
try {
|
|
117
|
+
await promise;
|
|
118
|
+
}
|
|
119
|
+
finally {
|
|
120
|
+
this.baselinePromises.delete(session);
|
|
86
121
|
}
|
|
87
|
-
|
|
122
|
+
}
|
|
123
|
+
async _generateBaselines(session) {
|
|
124
|
+
// Reconstruct from immutable open-time source, NOT from the live session.doc
|
|
125
|
+
// which may have been edited.
|
|
126
|
+
const doc = await DocxDocument.load(session.originalBuffer);
|
|
127
|
+
doc.normalize();
|
|
128
|
+
doc.insertParagraphBookmarks('_baseline');
|
|
129
|
+
const [clean, bookmarked] = await Promise.all([
|
|
130
|
+
doc.toBuffer({ cleanBookmarks: true }),
|
|
131
|
+
doc.toBuffer({ cleanBookmarks: false }),
|
|
132
|
+
]);
|
|
133
|
+
session.comparisonBaseline = clean.buffer;
|
|
134
|
+
session.comparisonBaselineWithBookmarks = bookmarked.buffer;
|
|
135
|
+
}
|
|
136
|
+
/** Get session by file path (auto-canonicalizes). */
|
|
137
|
+
async getSessionByFilePath(filePath) {
|
|
138
|
+
const canonical = await this.canonicalizePath(filePath);
|
|
139
|
+
return this.getSessionByPath(canonical);
|
|
140
|
+
}
|
|
141
|
+
/** Get session by canonical file path. Returns null if not found or expired. */
|
|
142
|
+
getSessionByPath(canonicalPath) {
|
|
143
|
+
const ses = this.sessions.get(canonicalPath);
|
|
88
144
|
if (!ses)
|
|
89
|
-
|
|
145
|
+
return null;
|
|
90
146
|
const now = Date.now();
|
|
91
147
|
if (ses.expiresAt.getTime() < now) {
|
|
92
|
-
this.sessions.delete(
|
|
93
|
-
|
|
148
|
+
this.sessions.delete(canonicalPath);
|
|
149
|
+
return null;
|
|
94
150
|
}
|
|
95
151
|
return ses;
|
|
96
152
|
}
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
153
|
+
/**
|
|
154
|
+
* @deprecated Use getSessionByPath instead. Kept only for backward compatibility during migration.
|
|
155
|
+
*/
|
|
156
|
+
getSession(sessionId) {
|
|
157
|
+
// Linear scan by sessionId — only used by legacy code paths
|
|
158
|
+
for (const [key, ses] of this.sessions.entries()) {
|
|
159
|
+
if (ses.sessionId === sessionId) {
|
|
160
|
+
const now = Date.now();
|
|
161
|
+
if (ses.expiresAt.getTime() < now) {
|
|
162
|
+
this.sessions.delete(key);
|
|
163
|
+
throw new Error(`SESSION_EXPIRED:${sessionId}`);
|
|
164
|
+
}
|
|
165
|
+
return ses;
|
|
104
166
|
}
|
|
105
|
-
if (this.normalizePath(session.originalPath) !== normalizedPath)
|
|
106
|
-
continue;
|
|
107
|
-
out.push(session);
|
|
108
167
|
}
|
|
109
|
-
|
|
110
|
-
return out;
|
|
111
|
-
}
|
|
112
|
-
getMostRecentlyUsedSessionForPath(normalizedPath) {
|
|
113
|
-
const sessionsForPath = this.listActiveSessionsForPath(normalizedPath);
|
|
114
|
-
return sessionsForPath[0] ?? null;
|
|
168
|
+
throw new Error(`SESSION_NOT_FOUND:${sessionId}`);
|
|
115
169
|
}
|
|
116
170
|
async cleanupSessionArtifacts(session) {
|
|
117
|
-
|
|
118
|
-
|
|
171
|
+
if (isDocxSession(session)) {
|
|
172
|
+
const tmpDir = path.dirname(session.tmpPath);
|
|
173
|
+
await fs.rm(tmpDir, { recursive: true, force: true }).catch(() => undefined);
|
|
174
|
+
}
|
|
175
|
+
// GDocs sessions have no tmp dir to clean up
|
|
119
176
|
}
|
|
120
|
-
async
|
|
121
|
-
|
|
122
|
-
|
|
177
|
+
async clearSessionByPath(filePath) {
|
|
178
|
+
// GDocs sessions use "gdocs:<docId>" keys — skip filesystem canonicalization
|
|
179
|
+
const sessionKey = filePath.startsWith('gdocs:')
|
|
180
|
+
? filePath
|
|
181
|
+
: await this.canonicalizePath(filePath);
|
|
182
|
+
const session = this.sessions.get(sessionKey);
|
|
183
|
+
if (!session)
|
|
184
|
+
return null;
|
|
185
|
+
this.sessions.delete(sessionKey);
|
|
123
186
|
await this.cleanupSessionArtifacts(session);
|
|
124
|
-
return
|
|
125
|
-
}
|
|
126
|
-
async clearSessionsByPath(normalizedPath) {
|
|
127
|
-
const sessionsForPath = this.listActiveSessionsForPath(normalizedPath);
|
|
128
|
-
for (const session of sessionsForPath) {
|
|
129
|
-
this.sessions.delete(session.sessionId);
|
|
130
|
-
}
|
|
131
|
-
await Promise.all(sessionsForPath.map((session) => this.cleanupSessionArtifacts(session)));
|
|
132
|
-
return sessionsForPath.map((session) => session.sessionId);
|
|
187
|
+
return sessionKey;
|
|
133
188
|
}
|
|
134
189
|
async clearAllSessions() {
|
|
135
|
-
const allSessions = [...this.sessions.
|
|
136
|
-
const
|
|
190
|
+
const allSessions = [...this.sessions.entries()];
|
|
191
|
+
const clearedPaths = allSessions.map(([key]) => key);
|
|
137
192
|
this.sessions.clear();
|
|
138
|
-
await Promise.all(allSessions.map((session) => this.cleanupSessionArtifacts(session)));
|
|
139
|
-
return
|
|
193
|
+
await Promise.all(allSessions.map(([, session]) => this.cleanupSessionArtifacts(session)));
|
|
194
|
+
return clearedPaths;
|
|
140
195
|
}
|
|
141
196
|
touch(session) {
|
|
142
197
|
const now = new Date();
|
|
@@ -146,10 +201,12 @@ export class SessionManager {
|
|
|
146
201
|
markEdited(session) {
|
|
147
202
|
session.editCount += 1;
|
|
148
203
|
session.editRevision += 1;
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
204
|
+
if (isDocxSession(session)) {
|
|
205
|
+
// Any edit creates a new canonical revision; previously generated artifacts
|
|
206
|
+
// are no longer current and should not be reused by default.
|
|
207
|
+
session.saveCache.clear();
|
|
208
|
+
session.extractionCache = null;
|
|
209
|
+
}
|
|
153
210
|
}
|
|
154
211
|
getSaveCache(session, cacheKey) {
|
|
155
212
|
return session.saveCache.get(cacheKey) ?? null;
|
|
@@ -169,6 +226,33 @@ export class SessionManager {
|
|
|
169
226
|
setExtractionCache(session, changes) {
|
|
170
227
|
session.extractionCache = { revision: session.editRevision, changes };
|
|
171
228
|
}
|
|
229
|
+
/**
|
|
230
|
+
* Create a Google Docs session. The `doc` is an already-loaded
|
|
231
|
+
* GoogleDocsDocument instance (created via dynamic import in the handler layer).
|
|
232
|
+
*/
|
|
233
|
+
createGDocsSession(docId, doc) {
|
|
234
|
+
const sessionKey = `gdocs:${docId}`;
|
|
235
|
+
const existing = this.sessions.get(sessionKey);
|
|
236
|
+
if (existing) {
|
|
237
|
+
this.touch(existing);
|
|
238
|
+
return existing;
|
|
239
|
+
}
|
|
240
|
+
const sessionId = this.newSessionId();
|
|
241
|
+
const now = new Date();
|
|
242
|
+
const session = {
|
|
243
|
+
provider: 'gdocs',
|
|
244
|
+
sessionId,
|
|
245
|
+
docId,
|
|
246
|
+
doc,
|
|
247
|
+
editCount: 0,
|
|
248
|
+
editRevision: 0,
|
|
249
|
+
createdAt: now,
|
|
250
|
+
lastAccessedAt: now,
|
|
251
|
+
expiresAt: new Date(now.getTime() + this.ttlMs),
|
|
252
|
+
};
|
|
253
|
+
this.sessions.set(sessionKey, session);
|
|
254
|
+
return session;
|
|
255
|
+
}
|
|
172
256
|
async saveTo(session, savePath, opts) {
|
|
173
257
|
const { buffer } = await session.doc.toBuffer({ cleanBookmarks: opts?.cleanBookmarks ?? true });
|
|
174
258
|
await fs.writeFile(savePath, new Uint8Array(buffer));
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"manager.js","sourceRoot":"","sources":["../../src/session/manager.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAE,MAAM,aAAa,CAAC;AAC1C,OAAO,IAAI,MAAM,WAAW,CAAC;AAC7B,OAAO,EAAE,MAAM,SAAS,CAAC;AACzB,OAAO,EAAE,MAAM,kBAAkB,CAAC;AAClC,OAAO,EACL,YAAY,GAMb,MAAM,sBAAsB,CAAC;
|
|
1
|
+
{"version":3,"file":"manager.js","sourceRoot":"","sources":["../../src/session/manager.ts"],"names":[],"mappings":"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"}
|