@remnic/core 9.3.583 → 9.3.585
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/index.js +11 -1
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
- package/src/projection/index.test.ts +28 -0
- package/src/projection/index.ts +12 -1
package/package.json
CHANGED
|
@@ -159,6 +159,34 @@ test("generateContextTree rejects symlinked memory category roots", async () =>
|
|
|
159
159
|
}
|
|
160
160
|
});
|
|
161
161
|
|
|
162
|
+
test("generateContextTree rejects symlinked memoryDir roots", async () => {
|
|
163
|
+
const root = await mkdtemp(path.join(os.tmpdir(), "remnic-projection-root-symlink-"));
|
|
164
|
+
try {
|
|
165
|
+
const outsideMemoryDir = path.join(root, "outside-memory");
|
|
166
|
+
const memoryDir = path.join(root, "memory");
|
|
167
|
+
const outputDir = path.join(root, "context-tree");
|
|
168
|
+
await writeFact(outsideMemoryDir);
|
|
169
|
+
await symlink(outsideMemoryDir, memoryDir, "dir");
|
|
170
|
+
|
|
171
|
+
await assert.rejects(
|
|
172
|
+
generateContextTree({
|
|
173
|
+
memoryDir,
|
|
174
|
+
outputDir,
|
|
175
|
+
categories: ["fact"],
|
|
176
|
+
includeEntities: false,
|
|
177
|
+
includeQuestions: false,
|
|
178
|
+
}),
|
|
179
|
+
/memoryDir must not be a symlink/,
|
|
180
|
+
);
|
|
181
|
+
await assert.rejects(
|
|
182
|
+
readFile(path.join(outputDir, "fact", "fact-1.md"), "utf-8"),
|
|
183
|
+
/ENOENT/,
|
|
184
|
+
);
|
|
185
|
+
} finally {
|
|
186
|
+
await rm(root, { recursive: true, force: true });
|
|
187
|
+
}
|
|
188
|
+
});
|
|
189
|
+
|
|
162
190
|
test("generateContextTree rejects symlinked output path components", async () => {
|
|
163
191
|
const root = await mkdtemp(path.join(os.tmpdir(), "remnic-projection-output-symlink-"));
|
|
164
192
|
try {
|
package/src/projection/index.ts
CHANGED
|
@@ -90,7 +90,7 @@ export async function generateContextTree(options: GenerateOptions): Promise<Gen
|
|
|
90
90
|
const resolvedMemoryDir = path.resolve(memoryDir);
|
|
91
91
|
const resolvedOutputDir = path.resolve(outputDir);
|
|
92
92
|
const requestedCategories = validateProjectionCategories(filterCategories);
|
|
93
|
-
const realMemoryDir =
|
|
93
|
+
const realMemoryDir = assertSafeMemoryRoot(resolvedMemoryDir);
|
|
94
94
|
|
|
95
95
|
// Ensure output directory exists
|
|
96
96
|
assertNotSymlink(resolvedOutputDir, "context tree outputDir");
|
|
@@ -240,6 +240,17 @@ function assertNotSymlink(targetPath: string, label: string): void {
|
|
|
240
240
|
}
|
|
241
241
|
}
|
|
242
242
|
|
|
243
|
+
function assertSafeMemoryRoot(targetPath: string): string {
|
|
244
|
+
const stat = fs.lstatSync(targetPath);
|
|
245
|
+
if (stat.isSymbolicLink()) {
|
|
246
|
+
throw new Error(`memoryDir must not be a symlink: ${targetPath}`);
|
|
247
|
+
}
|
|
248
|
+
if (!stat.isDirectory()) {
|
|
249
|
+
throw new Error(`memoryDir must be a directory: ${targetPath}`);
|
|
250
|
+
}
|
|
251
|
+
return fs.realpathSync(targetPath);
|
|
252
|
+
}
|
|
253
|
+
|
|
243
254
|
function assertSafeInputRoot(realMemoryDir: string, targetPath: string, label: string): void {
|
|
244
255
|
const stat = fs.lstatSync(targetPath);
|
|
245
256
|
if (stat.isSymbolicLink()) {
|