@tangle-network/braid 0.1.0 → 0.1.1
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/README.md +10 -0
- package/THIRD_PARTY_LICENSES.json +16 -0
- package/THIRD_PARTY_NOTICES.md +4 -1
- package/dist/adapters/analysis/managed-analysis-runtime.d.ts +19 -0
- package/dist/adapters/analysis/managed-analysis-runtime.d.ts.map +1 -0
- package/dist/adapters/analysis/managed-analysis-runtime.js +72 -0
- package/dist/adapters/analysis/managed-analysis-runtime.js.map +1 -0
- package/dist/adapters/analysis/production-analysis-analyst.d.ts +1 -1
- package/dist/adapters/analysis/production-analysis-analyst.d.ts.map +1 -1
- package/dist/adapters/analysis/production-analysis-analyst.js +12 -2
- package/dist/adapters/analysis/production-analysis-analyst.js.map +1 -1
- package/dist/adapters/analysis/python-runner.d.ts +3 -1
- package/dist/adapters/analysis/python-runner.d.ts.map +1 -1
- package/dist/adapters/analysis/python-runner.js +99 -1
- package/dist/adapters/analysis/python-runner.js.map +1 -1
- package/dist/adapters/analysis/trace-analysis-adapter.d.ts +2 -0
- package/dist/adapters/analysis/trace-analysis-adapter.d.ts.map +1 -1
- package/dist/adapters/analysis/trace-analysis-adapter.js +6 -0
- package/dist/adapters/analysis/trace-analysis-adapter.js.map +1 -1
- package/dist/adapters/credentials/headless-key.js +3 -2
- package/dist/adapters/credentials/headless-key.js.map +1 -1
- package/dist/adapters/persistence/posix-at.d.ts +8 -0
- package/dist/adapters/persistence/posix-at.d.ts.map +1 -0
- package/dist/adapters/persistence/posix-at.js +96 -0
- package/dist/adapters/persistence/posix-at.js.map +1 -0
- package/dist/adapters/persistence/safe-file-descriptor.d.ts +1 -1
- package/dist/adapters/persistence/safe-file-descriptor.d.ts.map +1 -1
- package/dist/adapters/persistence/safe-file-descriptor.js +29 -18
- package/dist/adapters/persistence/safe-file-descriptor.js.map +1 -1
- package/dist/adapters/persistence/safe-file-io.d.ts.map +1 -1
- package/dist/adapters/persistence/safe-file-io.js +9 -9
- package/dist/adapters/persistence/safe-file-io.js.map +1 -1
- package/dist/adapters/persistence/safe-file.d.ts +1 -1
- package/dist/adapters/persistence/safe-file.d.ts.map +1 -1
- package/dist/adapters/persistence/safe-file.js +4 -4
- package/dist/adapters/persistence/safe-file.js.map +1 -1
- package/dist/adapters/storage/sqlite-bound-open.d.ts +4 -4
- package/dist/adapters/storage/sqlite-bound-open.d.ts.map +1 -1
- package/dist/adapters/storage/sqlite-bound-open.js +49 -19
- package/dist/adapters/storage/sqlite-bound-open.js.map +1 -1
- package/dist/app/analysis-comparison-request.d.ts +1 -1
- package/dist/app/analysis-comparison-request.d.ts.map +1 -1
- package/dist/app/analysis-comparison-request.js +9 -5
- package/dist/app/analysis-comparison-request.js.map +1 -1
- package/dist/app/analysis-comparison.js +2 -2
- package/dist/app/analysis-comparison.js.map +1 -1
- package/dist/app/analysis-promotion.d.ts.map +1 -1
- package/dist/app/analysis-promotion.js +4 -5
- package/dist/app/analysis-promotion.js.map +1 -1
- package/dist/app/analysis-request.d.ts +1 -1
- package/dist/app/analysis-request.d.ts.map +1 -1
- package/dist/app/analysis-request.js +3 -7
- package/dist/app/analysis-request.js.map +1 -1
- package/dist/app/analysis-service.js +1 -1
- package/dist/app/analysis-service.js.map +1 -1
- package/dist/app/analysis-source.d.ts +4 -1
- package/dist/app/analysis-source.d.ts.map +1 -1
- package/dist/app/analysis-source.js +18 -0
- package/dist/app/analysis-source.js.map +1 -1
- package/dist/app/analysis-types.d.ts +1 -0
- package/dist/app/analysis-types.d.ts.map +1 -1
- package/dist/app/analysis-types.js.map +1 -1
- package/dist/app/application-support.d.ts +4 -0
- package/dist/app/application-support.d.ts.map +1 -1
- package/dist/app/application-support.js.map +1 -1
- package/dist/app/application.d.ts.map +1 -1
- package/dist/app/application.js +28 -7
- package/dist/app/application.js.map +1 -1
- package/dist/app/journal.d.ts +4 -0
- package/dist/app/journal.d.ts.map +1 -1
- package/dist/app/journal.js +6 -0
- package/dist/app/journal.js.map +1 -1
- package/dist/app/storage-journal.d.ts +4 -1
- package/dist/app/storage-journal.d.ts.map +1 -1
- package/dist/app/storage-journal.js +5 -0
- package/dist/app/storage-journal.js.map +1 -1
- package/dist/bin/plain.js +1 -1
- package/dist/bin/plain.js.map +1 -1
- package/dist/domain/ids-core.d.ts +1 -1
- package/dist/domain/ids-core.d.ts.map +1 -1
- package/dist/domain/ids-core.js +5 -2
- package/dist/domain/ids-core.js.map +1 -1
- package/dist/ports/effect-storage.d.ts +5 -0
- package/dist/ports/effect-storage.d.ts.map +1 -1
- package/dist/startup/durable-runtime.js +2 -344
- package/dist/startup/durable-runtime.js.map +1 -6
- package/dist/startup/preview-runtime.js +170 -6
- package/dist/startup/preview-runtime.js.map +1 -6
- package/dist/startup/terminal-runtime.js +5 -13
- package/dist/startup/terminal-runtime.js.map +1 -6
- package/dist/version.d.ts +1 -1
- package/dist/version.d.ts.map +1 -1
- package/dist/version.js +21 -1
- package/dist/version.js.map +1 -1
- package/dist/views/shared/semantic-details.d.ts.map +1 -1
- package/dist/views/shared/semantic-details.js +5 -0
- package/dist/views/shared/semantic-details.js.map +1 -1
- package/package.json +8 -3
- package/dist/startup/chunks/analysis-comparison-facts-BYZX2KTR.js +0 -2
- package/dist/startup/chunks/analysis-comparison-facts-BYZX2KTR.js.map +0 -6
- package/dist/startup/chunks/analysis-comparison-record-VMUVZPUV.js +0 -2
- package/dist/startup/chunks/analysis-comparison-record-VMUVZPUV.js.map +0 -6
- package/dist/startup/chunks/chunk-2B6P3EZQ.js +0 -2
- package/dist/startup/chunks/chunk-2B6P3EZQ.js.map +0 -6
- package/dist/startup/chunks/chunk-3SLVNOQZ.js +0 -2
- package/dist/startup/chunks/chunk-3SLVNOQZ.js.map +0 -6
- package/dist/startup/chunks/chunk-5ZIGORCF.js +0 -6
- package/dist/startup/chunks/chunk-5ZIGORCF.js.map +0 -6
- package/dist/startup/chunks/chunk-6G7QKB6J.js +0 -2
- package/dist/startup/chunks/chunk-6G7QKB6J.js.map +0 -6
- package/dist/startup/chunks/chunk-AUAERYTD.js +0 -2
- package/dist/startup/chunks/chunk-AUAERYTD.js.map +0 -6
- package/dist/startup/chunks/chunk-BCT2WD5R.js +0 -2
- package/dist/startup/chunks/chunk-BCT2WD5R.js.map +0 -6
- package/dist/startup/chunks/chunk-ECYRVU25.js +0 -2
- package/dist/startup/chunks/chunk-ECYRVU25.js.map +0 -6
- package/dist/startup/chunks/chunk-EQDIVTWX.js +0 -2
- package/dist/startup/chunks/chunk-EQDIVTWX.js.map +0 -6
- package/dist/startup/chunks/chunk-FRHYXPNB.js +0 -2
- package/dist/startup/chunks/chunk-FRHYXPNB.js.map +0 -6
- package/dist/startup/chunks/chunk-GZKMBTCI.js +0 -3
- package/dist/startup/chunks/chunk-GZKMBTCI.js.map +0 -6
- package/dist/startup/chunks/chunk-GZLREBOD.js +0 -2
- package/dist/startup/chunks/chunk-GZLREBOD.js.map +0 -6
- package/dist/startup/chunks/chunk-HFZ5Q3X5.js +0 -2
- package/dist/startup/chunks/chunk-HFZ5Q3X5.js.map +0 -6
- package/dist/startup/chunks/chunk-ICFZ5GZR.js +0 -2
- package/dist/startup/chunks/chunk-ICFZ5GZR.js.map +0 -6
- package/dist/startup/chunks/chunk-JR4A5QXZ.js +0 -2
- package/dist/startup/chunks/chunk-JR4A5QXZ.js.map +0 -6
- package/dist/startup/chunks/chunk-LUXHNCKY.js +0 -2
- package/dist/startup/chunks/chunk-LUXHNCKY.js.map +0 -6
- package/dist/startup/chunks/chunk-NDSFD5HI.js +0 -2
- package/dist/startup/chunks/chunk-NDSFD5HI.js.map +0 -6
- package/dist/startup/chunks/chunk-NWDQFVYZ.js +0 -6
- package/dist/startup/chunks/chunk-NWDQFVYZ.js.map +0 -6
- package/dist/startup/chunks/chunk-PAPTIOCL.js +0 -2
- package/dist/startup/chunks/chunk-PAPTIOCL.js.map +0 -6
- package/dist/startup/chunks/chunk-PIJUYQ3B.js +0 -2
- package/dist/startup/chunks/chunk-PIJUYQ3B.js.map +0 -6
- package/dist/startup/chunks/chunk-PXRVFPRL.js +0 -2
- package/dist/startup/chunks/chunk-PXRVFPRL.js.map +0 -6
- package/dist/startup/chunks/chunk-RELMHYIG.js +0 -3
- package/dist/startup/chunks/chunk-RELMHYIG.js.map +0 -6
- package/dist/startup/chunks/chunk-RJAXEI5Z.js +0 -2
- package/dist/startup/chunks/chunk-RJAXEI5Z.js.map +0 -6
- package/dist/startup/chunks/chunk-RPJ2AWHI.js +0 -2
- package/dist/startup/chunks/chunk-RPJ2AWHI.js.map +0 -6
- package/dist/startup/chunks/chunk-TW2LBTSL.js +0 -2
- package/dist/startup/chunks/chunk-TW2LBTSL.js.map +0 -6
- package/dist/startup/chunks/chunk-TYNDYSMP.js +0 -2
- package/dist/startup/chunks/chunk-TYNDYSMP.js.map +0 -6
- package/dist/startup/chunks/chunk-TZNTMUGF.js +0 -117
- package/dist/startup/chunks/chunk-TZNTMUGF.js.map +0 -6
- package/dist/startup/chunks/chunk-UT4NB43O.js +0 -2
- package/dist/startup/chunks/chunk-UT4NB43O.js.map +0 -6
- package/dist/startup/chunks/chunk-VTNLVERY.js +0 -2
- package/dist/startup/chunks/chunk-VTNLVERY.js.map +0 -6
- package/dist/startup/chunks/configuration-wizard-G5VQFNBR.js +0 -3
- package/dist/startup/chunks/configuration-wizard-G5VQFNBR.js.map +0 -6
- package/dist/startup/chunks/production-connection-providers-3BNIYUIS.js +0 -2
- package/dist/startup/chunks/production-connection-providers-3BNIYUIS.js.map +0 -6
- package/dist/startup/chunks/production-connections-27KWJIR6.js +0 -2
- package/dist/startup/chunks/production-connections-27KWJIR6.js.map +0 -6
- package/dist/startup/chunks/profile-connection-dispatch-HFTWSEIR.js +0 -2
- package/dist/startup/chunks/profile-connection-dispatch-HFTWSEIR.js.map +0 -6
- package/dist/startup/chunks/supervisor-control-VPVKE7NI.js +0 -2
- package/dist/startup/chunks/supervisor-control-VPVKE7NI.js.map +0 -6
- package/dist/startup/chunks/supervisor-watch-X6TXO6GN.js +0 -2
- package/dist/startup/chunks/supervisor-watch-X6TXO6GN.js.map +0 -6
- package/dist/startup/chunks/trace-store-ZIU4S2VR.js +0 -6
- package/dist/startup/chunks/trace-store-ZIU4S2VR.js.map +0 -6
- package/dist/startup/chunks/ui-dispatch-NV3XTZDR.js +0 -3
- package/dist/startup/chunks/ui-dispatch-NV3XTZDR.js.map +0 -6
|
@@ -0,0 +1,96 @@
|
|
|
1
|
+
import { readlinkSync } from 'node:fs';
|
|
2
|
+
import koffi from 'koffi';
|
|
3
|
+
let cachedBindings;
|
|
4
|
+
function bindings() {
|
|
5
|
+
if (process.platform !== 'darwin' && process.platform !== 'linux') {
|
|
6
|
+
const error = new Error(`Descriptor-relative filesystem operations are unavailable on ${process.platform}`);
|
|
7
|
+
error.code = 'ENOSYS';
|
|
8
|
+
error.syscall = 'openat';
|
|
9
|
+
throw error;
|
|
10
|
+
}
|
|
11
|
+
if (cachedBindings !== undefined)
|
|
12
|
+
return cachedBindings;
|
|
13
|
+
const libc = koffi.load(null);
|
|
14
|
+
cachedBindings = {
|
|
15
|
+
fcntl: libc.func('int fcntl(int fileDescriptor, int command, ...)'),
|
|
16
|
+
linkAt: libc.func('int linkat(int sourceDirectory, const char *source, int targetDirectory, const char *target, int flags)'),
|
|
17
|
+
mkdirAt: libc.func('int mkdirat(int directory, const char *path, unsigned int mode)'),
|
|
18
|
+
openAt: libc.func('int openat(int directory, const char *path, int flags, ...)'),
|
|
19
|
+
renameAt: libc.func('int renameat(int sourceDirectory, const char *source, int targetDirectory, const char *target)'),
|
|
20
|
+
unlinkAt: libc.func('int unlinkat(int directory, const char *path, int flags)'),
|
|
21
|
+
};
|
|
22
|
+
return cachedBindings;
|
|
23
|
+
}
|
|
24
|
+
const DARWIN_F_GETPATH = 50;
|
|
25
|
+
const DARWIN_MAX_PATH_LENGTH = 1024;
|
|
26
|
+
const CLOSE_ON_EXEC = process.platform === 'darwin' ? 0x01000000 : 0o2000000;
|
|
27
|
+
export function descriptorTargetPath(fileDescriptor) {
|
|
28
|
+
if (process.platform === 'linux')
|
|
29
|
+
return readlinkSync(`/proc/self/fd/${fileDescriptor}`);
|
|
30
|
+
if (process.platform !== 'darwin') {
|
|
31
|
+
const error = new Error(`Descriptor target paths are unavailable on ${process.platform}`);
|
|
32
|
+
error.code = 'ENOSYS';
|
|
33
|
+
error.syscall = 'fcntl';
|
|
34
|
+
throw error;
|
|
35
|
+
}
|
|
36
|
+
const output = Buffer.alloc(DARWIN_MAX_PATH_LENGTH);
|
|
37
|
+
const result = bindings().fcntl(fileDescriptor, DARWIN_F_GETPATH, 'void *', output);
|
|
38
|
+
if (result < 0)
|
|
39
|
+
throw syscallError('fcntl', String(fileDescriptor));
|
|
40
|
+
const terminator = output.indexOf(0);
|
|
41
|
+
if (terminator <= 0) {
|
|
42
|
+
const error = new Error('Darwin F_GETPATH returned an invalid path');
|
|
43
|
+
error.code = 'EIO';
|
|
44
|
+
error.path = String(fileDescriptor);
|
|
45
|
+
error.syscall = 'fcntl';
|
|
46
|
+
throw error;
|
|
47
|
+
}
|
|
48
|
+
return output.toString('utf8', 0, terminator);
|
|
49
|
+
}
|
|
50
|
+
export function descriptorPath(fileDescriptor) {
|
|
51
|
+
if (process.platform === 'linux')
|
|
52
|
+
return `/proc/self/fd/${fileDescriptor}`;
|
|
53
|
+
return descriptorTargetPath(fileDescriptor);
|
|
54
|
+
}
|
|
55
|
+
function errnoCode(errno) {
|
|
56
|
+
for (const [name, value] of Object.entries(koffi.os.errno)) {
|
|
57
|
+
if (value === errno && name.startsWith('E'))
|
|
58
|
+
return name;
|
|
59
|
+
}
|
|
60
|
+
return `ERRNO_${errno}`;
|
|
61
|
+
}
|
|
62
|
+
function syscallError(syscall, path) {
|
|
63
|
+
const errno = koffi.errno();
|
|
64
|
+
const code = errnoCode(errno);
|
|
65
|
+
const error = new Error(`${code}: ${syscall} '${path}'`);
|
|
66
|
+
error.code = code;
|
|
67
|
+
error.errno = errno;
|
|
68
|
+
error.path = path;
|
|
69
|
+
error.syscall = syscall;
|
|
70
|
+
return error;
|
|
71
|
+
}
|
|
72
|
+
export function openAt(directory, path, flags, mode = 0) {
|
|
73
|
+
const result = bindings().openAt(directory, path, flags | CLOSE_ON_EXEC, 'unsigned int', mode);
|
|
74
|
+
if (result < 0)
|
|
75
|
+
throw syscallError('openat', path);
|
|
76
|
+
return result;
|
|
77
|
+
}
|
|
78
|
+
export function mkdirAt(directory, path, mode) {
|
|
79
|
+
if (bindings().mkdirAt(directory, path, mode) < 0)
|
|
80
|
+
throw syscallError('mkdirat', path);
|
|
81
|
+
}
|
|
82
|
+
export function unlinkAt(directory, path) {
|
|
83
|
+
if (bindings().unlinkAt(directory, path, 0) < 0)
|
|
84
|
+
throw syscallError('unlinkat', path);
|
|
85
|
+
}
|
|
86
|
+
export function renameAt(sourceDirectory, source, targetDirectory, target) {
|
|
87
|
+
if (bindings().renameAt(sourceDirectory, source, targetDirectory, target) < 0) {
|
|
88
|
+
throw syscallError('renameat', target);
|
|
89
|
+
}
|
|
90
|
+
}
|
|
91
|
+
export function linkAt(sourceDirectory, source, targetDirectory, target) {
|
|
92
|
+
if (bindings().linkAt(sourceDirectory, source, targetDirectory, target, 0) < 0) {
|
|
93
|
+
throw syscallError('linkat', target);
|
|
94
|
+
}
|
|
95
|
+
}
|
|
96
|
+
//# sourceMappingURL=posix-at.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"posix-at.js","sourceRoot":"","sources":["../../../src/adapters/persistence/posix-at.ts"],"names":[],"mappings":"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"}
|
|
@@ -20,12 +20,12 @@ export interface OpenParent {
|
|
|
20
20
|
export declare function errorCode(error: unknown): string | undefined;
|
|
21
21
|
export declare function safePath(path: string): SafePath;
|
|
22
22
|
export declare function componentPath(path: SafePath, count: number): string;
|
|
23
|
-
export declare function childPath(directoryFd: number, leaf: string): string;
|
|
24
23
|
export declare function normalizePathError(error: unknown, path: string): unknown;
|
|
25
24
|
export declare function requireDirectory(handle: number, path: string): void;
|
|
26
25
|
export declare function requireRegularFile(handle: number, path: string): void;
|
|
27
26
|
export declare function openDirectoryComponents(path: SafePath, count: number): number;
|
|
28
27
|
export declare function openParent(path: string): OpenParent;
|
|
28
|
+
export declare function openChild(directoryFd: number, leaf: string, path: string, flags: number, mode?: number): number;
|
|
29
29
|
export declare function openLeaf(parent: OpenParent, flags: number, mode?: number): number;
|
|
30
30
|
export declare function openExistingLeaf(path: string): number;
|
|
31
31
|
export declare function unlinkAt(parentFd: number, leaf: string, path: string): void;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"safe-file-descriptor.d.ts","sourceRoot":"","sources":["../../../src/adapters/persistence/safe-file-descriptor.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"safe-file-descriptor.d.ts","sourceRoot":"","sources":["../../../src/adapters/persistence/safe-file-descriptor.ts"],"names":[],"mappings":"AAQA,QAAA,MAAM,eAAe,QAAmE,CAAA;AACxF,QAAA,MAAM,UAAU,QAAmE,CAAA;AAKnF,MAAM,MAAM,iBAAiB,GACzB,yBAAyB,GACzB,wBAAwB,GACxB,0BAA0B,GAC1B,yBAAyB,GACzB,uBAAuB,GACvB,iCAAiC,GACjC,6BAA6B,GAC7B,mBAAmB,CAAA;AAEvB,gEAAgE;AAChE,qBAAa,aAAc,SAAQ,KAAK;IACtC,QAAQ,CAAC,IAAI,EAAE,iBAAiB,CAAA;IAEhC,YAAY,IAAI,EAAE,iBAAiB,EAAE,OAAO,EAAE,MAAM,EAInD;CACF;AAED,MAAM,WAAW,QAAQ;IACvB,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAA;IACzB,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAA;IACrB,QAAQ,CAAC,UAAU,EAAE,SAAS,MAAM,EAAE,CAAA;CACvC;AAED,MAAM,WAAW,UAAU;IACzB,QAAQ,CAAC,IAAI,EAAE,QAAQ,CAAA;IACvB,QAAQ,CAAC,EAAE,EAAE,MAAM,CAAA;IACnB,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAA;IACrB,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAA;CAC1B;AAUD,wBAAgB,SAAS,CAAC,KAAK,EAAE,OAAO,GAAG,MAAM,GAAG,SAAS,CAI5D;AAED,wBAAgB,QAAQ,CAAC,IAAI,EAAE,MAAM,GAAG,QAAQ,CAkB/C;AAED,wBAAgB,aAAa,CAAC,IAAI,EAAE,QAAQ,EAAE,KAAK,EAAE,MAAM,GAAG,MAAM,CAEnE;AAiBD,wBAAgB,kBAAkB,CAAC,KAAK,EAAE,OAAO,EAAE,IAAI,EAAE,MAAM,GAAG,OAAO,CAQxE;AAED,wBAAgB,gBAAgB,CAAC,MAAM,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,GAAG,IAAI,CAOnE;AAED,wBAAgB,kBAAkB,CAAC,MAAM,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,GAAG,IAAI,CAOrE;AAED,wBAAgB,uBAAuB,CAAC,IAAI,EAAE,QAAQ,EAAE,KAAK,EAAE,MAAM,GAAG,MAAM,CAgC7E;AAED,wBAAgB,UAAU,CAAC,IAAI,EAAE,MAAM,GAAG,UAAU,CAwBnD;AAED,wBAAgB,SAAS,CACvB,WAAW,EAAE,MAAM,EACnB,IAAI,EAAE,MAAM,EACZ,IAAI,EAAE,MAAM,EACZ,KAAK,EAAE,MAAM,EACb,IAAI,CAAC,EAAE,MAAM,GACZ,MAAM,CASR;AAED,wBAAgB,QAAQ,CAAC,MAAM,EAAE,UAAU,EAAE,KAAK,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE,MAAM,GAAG,MAAM,CAEjF;AAED,wBAAgB,gBAAgB,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CA6BrD;AAED,wBAAgB,QAAQ,CAAC,QAAQ,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,GAAG,IAAI,CAO3E;AAED,qGAAqG;AACrG,wBAAgB,mBAAmB,CAAC,IAAI,EAAE,MAAM,GAAG,IAAI,CAqBtD;AAED,sFAAsF;AACtF,wBAAgB,mBAAmB,CAAC,IAAI,EAAE,MAAM,GAAG,IAAI,CAItD;AAED,sFAAsF;AACtF,wBAAgB,sBAAsB,CAAC,IAAI,EAAE,MAAM,EAAE,IAAI,SAAQ,GAAG,IAAI,CAwCvE;AAED,OAAO,EAAE,eAAe,EAAE,UAAU,EAAE,CAAA"}
|
|
@@ -1,5 +1,6 @@
|
|
|
1
|
-
import { closeSync, constants, fstatSync,
|
|
1
|
+
import { closeSync, constants, fstatSync, openSync } from 'node:fs';
|
|
2
2
|
import { join, parse, resolve, sep } from 'node:path';
|
|
3
|
+
import { mkdirAt as mkdirRelative, openAt as openRelative, unlinkAt as unlinkRelative, } from './posix-at.js';
|
|
3
4
|
const DIRECTORY_FLAGS = constants.O_RDONLY | constants.O_NONBLOCK | constants.O_NOFOLLOW;
|
|
4
5
|
const LEAF_FLAGS = constants.O_RDONLY | constants.O_NONBLOCK | constants.O_NOFOLLOW;
|
|
5
6
|
/** A fail-closed error from the private filesystem boundary. */
|
|
@@ -11,11 +12,9 @@ export class SafeFileError extends Error {
|
|
|
11
12
|
this.code = code;
|
|
12
13
|
}
|
|
13
14
|
}
|
|
14
|
-
function
|
|
15
|
-
if (process.platform === 'linux')
|
|
16
|
-
return
|
|
17
|
-
if (process.platform === 'darwin')
|
|
18
|
-
return '/dev/fd';
|
|
15
|
+
function assertSupportedPlatform() {
|
|
16
|
+
if (process.platform === 'linux' || process.platform === 'darwin')
|
|
17
|
+
return;
|
|
19
18
|
throw new SafeFileError('SAFE_FILE_PATH_RACE_UNSUPPORTED', `Descriptor-relative private-file access is unavailable on ${process.platform}; refusing the unsafe path operation`);
|
|
20
19
|
}
|
|
21
20
|
export function errorCode(error) {
|
|
@@ -25,7 +24,7 @@ export function errorCode(error) {
|
|
|
25
24
|
return typeof code === 'string' ? code : undefined;
|
|
26
25
|
}
|
|
27
26
|
export function safePath(path) {
|
|
28
|
-
|
|
27
|
+
assertSupportedPlatform();
|
|
29
28
|
if (path.includes('\u0000')) {
|
|
30
29
|
throw new SafeFileError('SAFE_FILE_INVALID_PATH', 'Private storage paths must not contain NUL bytes');
|
|
31
30
|
}
|
|
@@ -40,7 +39,7 @@ export function safePath(path) {
|
|
|
40
39
|
export function componentPath(path, count) {
|
|
41
40
|
return join(path.root, ...path.components.slice(0, count));
|
|
42
41
|
}
|
|
43
|
-
|
|
42
|
+
function assertLeaf(leaf) {
|
|
44
43
|
if (leaf.length === 0 ||
|
|
45
44
|
leaf === '.' ||
|
|
46
45
|
leaf === '..' ||
|
|
@@ -48,7 +47,6 @@ export function childPath(directoryFd, leaf) {
|
|
|
48
47
|
leaf.includes('\\')) {
|
|
49
48
|
throw new SafeFileError('SAFE_FILE_INVALID_PATH', 'Private storage path contains an invalid component');
|
|
50
49
|
}
|
|
51
|
-
return `${descriptorRoot()}/${directoryFd}/${leaf}`;
|
|
52
50
|
}
|
|
53
51
|
export function normalizePathError(error, path) {
|
|
54
52
|
if (errorCode(error) === 'ELOOP') {
|
|
@@ -76,7 +74,8 @@ export function openDirectoryComponents(path, count) {
|
|
|
76
74
|
const nextPath = join(currentPath, component);
|
|
77
75
|
let nextFd;
|
|
78
76
|
try {
|
|
79
|
-
|
|
77
|
+
assertLeaf(component);
|
|
78
|
+
nextFd = openRelative(currentFd, component, DIRECTORY_FLAGS);
|
|
80
79
|
}
|
|
81
80
|
catch (error) {
|
|
82
81
|
throw normalizePathError(error, nextPath);
|
|
@@ -121,16 +120,20 @@ export function openParent(path) {
|
|
|
121
120
|
leafPath: join(componentPath(parsed, parentCount), leaf),
|
|
122
121
|
};
|
|
123
122
|
}
|
|
124
|
-
export function
|
|
123
|
+
export function openChild(directoryFd, leaf, path, flags, mode) {
|
|
124
|
+
assertLeaf(leaf);
|
|
125
125
|
try {
|
|
126
126
|
return mode === undefined
|
|
127
|
-
?
|
|
128
|
-
:
|
|
127
|
+
? openRelative(directoryFd, leaf, flags)
|
|
128
|
+
: openRelative(directoryFd, leaf, flags, mode);
|
|
129
129
|
}
|
|
130
130
|
catch (error) {
|
|
131
|
-
throw normalizePathError(error,
|
|
131
|
+
throw normalizePathError(error, path);
|
|
132
132
|
}
|
|
133
133
|
}
|
|
134
|
+
export function openLeaf(parent, flags, mode) {
|
|
135
|
+
return openChild(parent.fd, parent.leaf, parent.leafPath, flags, mode);
|
|
136
|
+
}
|
|
134
137
|
export function openExistingLeaf(path) {
|
|
135
138
|
const parsed = safePath(path);
|
|
136
139
|
if (parsed.components.length === 0) {
|
|
@@ -167,8 +170,9 @@ export function openExistingLeaf(path) {
|
|
|
167
170
|
}
|
|
168
171
|
}
|
|
169
172
|
export function unlinkAt(parentFd, leaf, path) {
|
|
173
|
+
assertLeaf(leaf);
|
|
170
174
|
try {
|
|
171
|
-
|
|
175
|
+
unlinkRelative(parentFd, leaf);
|
|
172
176
|
}
|
|
173
177
|
catch (error) {
|
|
174
178
|
if (errorCode(error) !== 'ENOENT')
|
|
@@ -226,14 +230,15 @@ export function ensurePrivateDirectory(path, mode = 0o700) {
|
|
|
226
230
|
let nextFd;
|
|
227
231
|
for (;;) {
|
|
228
232
|
try {
|
|
229
|
-
|
|
233
|
+
assertLeaf(component);
|
|
234
|
+
nextFd = openRelative(currentFd, component, DIRECTORY_FLAGS);
|
|
230
235
|
break;
|
|
231
236
|
}
|
|
232
237
|
catch (error) {
|
|
233
238
|
if (errorCode(error) !== 'ENOENT')
|
|
234
239
|
throw normalizePathError(error, nextPath);
|
|
235
240
|
try {
|
|
236
|
-
|
|
241
|
+
mkdirRelative(currentFd, component, mode);
|
|
237
242
|
}
|
|
238
243
|
catch (mkdirError) {
|
|
239
244
|
if (errorCode(mkdirError) !== 'EEXIST') {
|
|
@@ -242,7 +247,13 @@ export function ensurePrivateDirectory(path, mode = 0o700) {
|
|
|
242
247
|
}
|
|
243
248
|
}
|
|
244
249
|
}
|
|
245
|
-
|
|
250
|
+
try {
|
|
251
|
+
requireDirectory(nextFd, nextPath);
|
|
252
|
+
}
|
|
253
|
+
catch (error) {
|
|
254
|
+
closeSync(nextFd);
|
|
255
|
+
throw error;
|
|
256
|
+
}
|
|
246
257
|
const previousFd = currentFd;
|
|
247
258
|
currentFd = nextFd;
|
|
248
259
|
currentPath = nextPath;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"safe-file-descriptor.js","sourceRoot":"","sources":["../../../src/adapters/persistence/safe-file-descriptor.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,SAAS,EAAE,SAAS,EAAE,
|
|
1
|
+
{"version":3,"file":"safe-file-descriptor.js","sourceRoot":"","sources":["../../../src/adapters/persistence/safe-file-descriptor.ts"],"names":[],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"safe-file-io.d.ts","sourceRoot":"","sources":["../../../src/adapters/persistence/safe-file-io.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"safe-file-io.d.ts","sourceRoot":"","sources":["../../../src/adapters/persistence/safe-file-io.ts"],"names":[],"mappings":"AAqCA,MAAM,WAAW,uBAAuB;IACtC,QAAQ,CAAC,SAAS,EAAE,OAAO,CAAA;IAC3B,QAAQ,CAAC,QAAQ,CAAC,EAAE,CAAC,OAAO,EAAE,MAAM,GAAG,SAAS,KAAK,IAAI,CAAA;IACzD,QAAQ,CAAC,gBAAgB,CAAC,EAAE,MAAM,CAAA;IAClC,QAAQ,CAAC,MAAM,CAAC,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,CAAA;IACzC,QAAQ,CAAC,OAAO,CAAC,EAAE,CAAC,KAAK,EAAE,qBAAqB,KAAK,IAAI,CAAA;CAC1D;AAED,MAAM,MAAM,qBAAqB,GAC7B,mBAAmB,GACnB,mBAAmB,GACnB,SAAS,GACT,mBAAmB,CAAA;AAiCvB,wBAAgB,MAAM,CACpB,WAAW,EAAE,MAAM,EACnB,IAAI,EAAE,MAAM,EACZ,IAAI,EAAE,MAAM,EACZ,QAAQ,EAAE,MAAM,GACf,MAAM,GAAG,SAAS,CAapB;AAuDD,wBAAgB,YAAY,CAAC,IAAI,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,GAAG,MAAM,GAAG,SAAS,CAY/E;AAED,4EAA4E;AAC5E,wBAAgB,iBAAiB,CAAC,IAAI,EAAE,MAAM,GAAG,IAAI,CAkBpD;AAED,wBAAgB,iBAAiB,CAAC,IAAI,EAAE,MAAM,GAAG,IAAI,CAWpD;AAED,wBAAgB,cAAc,CAAC,IAAI,EAAE,MAAM,GAAG,IAAI,CAQjD;AAED;;;;;;GAMG;AACH,wBAAgB,kBAAkB,CAChC,IAAI,EAAE,MAAM,EACZ,KAAK,EAAE,MAAM,GAAG,MAAM,EACtB,OAAO,EAAE,uBAAuB,GAC/B,IAAI,CAwEN;AAED,wBAAgB,gBAAgB,CAAC,IAAI,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAE3E"}
|
|
@@ -1,7 +1,8 @@
|
|
|
1
1
|
import { randomUUID } from 'node:crypto';
|
|
2
|
-
import { closeSync, constants, fchmodSync, fstatSync, fsyncSync,
|
|
2
|
+
import { closeSync, constants, fchmodSync, fstatSync, fsyncSync, readSync, writeSync, } from 'node:fs';
|
|
3
3
|
import { join } from 'node:path';
|
|
4
|
-
import {
|
|
4
|
+
import { linkAt, renameAt } from './posix-at.js';
|
|
5
|
+
import { componentPath, errorCode, normalizePathError, openChild, openDirectoryComponents, openExistingLeaf, openLeaf, openParent, requireRegularFile, SafeFileError, safePath, unlinkAt, } from './safe-file-descriptor.js';
|
|
5
6
|
const CREATE_FLAGS =
|
|
6
7
|
// O_EXCL makes the directory entry creation no-clobber; the temporary publication is anchored below.
|
|
7
8
|
constants.O_WRONLY |
|
|
@@ -39,7 +40,7 @@ export function readAt(directoryFd, leaf, path, maxBytes) {
|
|
|
39
40
|
let handle;
|
|
40
41
|
try {
|
|
41
42
|
try {
|
|
42
|
-
handle =
|
|
43
|
+
handle = openChild(directoryFd, leaf, path, safeLeafFlags());
|
|
43
44
|
}
|
|
44
45
|
catch (error) {
|
|
45
46
|
if (errorCode(error) === 'ENOENT')
|
|
@@ -81,13 +82,14 @@ function writeAll(handle, bytes) {
|
|
|
81
82
|
}
|
|
82
83
|
}
|
|
83
84
|
function writeTemporary(parent, temporary, bytes, onPhase) {
|
|
85
|
+
const temporaryPath = join(componentPath(parent.path, parent.path.components.length - 1), temporary);
|
|
84
86
|
let handle;
|
|
85
87
|
try {
|
|
86
88
|
try {
|
|
87
|
-
handle =
|
|
89
|
+
handle = openChild(parent.fd, temporary, temporaryPath, CREATE_FLAGS, 0o600);
|
|
88
90
|
}
|
|
89
91
|
catch (error) {
|
|
90
|
-
throw normalizePathError(error,
|
|
92
|
+
throw normalizePathError(error, temporaryPath);
|
|
91
93
|
}
|
|
92
94
|
requireRegularFile(handle, `${parent.leafPath}.${temporary}`);
|
|
93
95
|
writeAll(handle, bytes);
|
|
@@ -196,13 +198,11 @@ export function replacePrivateFile(path, value, options) {
|
|
|
196
198
|
throw new SafeFileError('SAFE_FILE_PUBLISHED_INVALID', `Private storage temporary file could not be verified: ${temporaryPath}`);
|
|
197
199
|
}
|
|
198
200
|
options.verify?.(written);
|
|
199
|
-
const source = childPath(parent.fd, temporary);
|
|
200
|
-
const target = childPath(parent.fd, parent.leaf);
|
|
201
201
|
try {
|
|
202
202
|
if (options.overwrite)
|
|
203
|
-
|
|
203
|
+
renameAt(parent.fd, temporary, parent.fd, parent.leaf);
|
|
204
204
|
else
|
|
205
|
-
|
|
205
|
+
linkAt(parent.fd, temporary, parent.fd, parent.leaf);
|
|
206
206
|
}
|
|
207
207
|
catch (error) {
|
|
208
208
|
throw normalizePathError(error, parent.leafPath);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"safe-file-io.js","sourceRoot":"","sources":["../../../src/adapters/persistence/safe-file-io.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,MAAM,aAAa,CAAA;AACxC,OAAO,EACL,SAAS,EACT,SAAS,EACT,UAAU,EACV,SAAS,EACT,SAAS,EACT,QAAQ,EACR,
|
|
1
|
+
{"version":3,"file":"safe-file-io.js","sourceRoot":"","sources":["../../../src/adapters/persistence/safe-file-io.ts"],"names":[],"mappings":"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"}
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
export { assertNoSymlinkPath, assertSafeDirectory, ensurePrivateDirectory, SafeFileError, type SafeFileErrorCode, } from './safe-file-descriptor.js';
|
|
2
|
-
export { ensurePrivateFile, fsyncDirectory,
|
|
2
|
+
export { ensurePrivateFile, fsyncDirectory, type PrivateFileWriteOptions, readNoFollow, removePrivateFile, replacePrivateFile, writePrivateFile, } from './safe-file-io.js';
|
|
3
3
|
/** A small crash-recovery lock; stale owners are safe to reclaim within the opened parent directory. */
|
|
4
4
|
export declare function acquirePrivateFileLock(path: string, description?: string): number;
|
|
5
5
|
export declare function releasePrivateFileLock(path: string, handle: number): void;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"safe-file.d.ts","sourceRoot":"","sources":["../../../src/adapters/persistence/safe-file.ts"],"names":[],"mappings":"AAaA,OAAO,EACL,mBAAmB,EACnB,mBAAmB,EACnB,sBAAsB,EACtB,aAAa,EACb,KAAK,iBAAiB,GACvB,MAAM,2BAA2B,CAAA;AAClC,OAAO,EACL,iBAAiB,EACjB,cAAc,EACd,
|
|
1
|
+
{"version":3,"file":"safe-file.d.ts","sourceRoot":"","sources":["../../../src/adapters/persistence/safe-file.ts"],"names":[],"mappings":"AAaA,OAAO,EACL,mBAAmB,EACnB,mBAAmB,EACnB,sBAAsB,EACtB,aAAa,EACb,KAAK,iBAAiB,GACvB,MAAM,2BAA2B,CAAA;AAClC,OAAO,EACL,iBAAiB,EACjB,cAAc,EACd,KAAK,uBAAuB,EAC5B,YAAY,EACZ,iBAAiB,EACjB,kBAAkB,EAClB,gBAAgB,GACjB,MAAM,mBAAmB,CAAA;AAc1B,wGAAwG;AACxG,wBAAgB,sBAAsB,CAAC,IAAI,EAAE,MAAM,EAAE,WAAW,SAAoB,GAAG,MAAM,CAiD5F;AAED,wBAAgB,sBAAsB,CAAC,IAAI,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,IAAI,CA0BzE"}
|
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
import { closeSync, constants, fsyncSync,
|
|
2
|
-
import {
|
|
1
|
+
import { closeSync, constants, fsyncSync, writeSync } from 'node:fs';
|
|
2
|
+
import { errorCode, normalizePathError, openLeaf, openParent, requireRegularFile, SafeFileError, unlinkAt, } from './safe-file-descriptor.js';
|
|
3
3
|
import { readAt } from './safe-file-io.js';
|
|
4
4
|
export { assertNoSymlinkPath, assertSafeDirectory, ensurePrivateDirectory, SafeFileError, } from './safe-file-descriptor.js';
|
|
5
|
-
export { ensurePrivateFile, fsyncDirectory,
|
|
5
|
+
export { ensurePrivateFile, fsyncDirectory, readNoFollow, removePrivateFile, replacePrivateFile, writePrivateFile, } from './safe-file-io.js';
|
|
6
6
|
const CREATE_FLAGS = constants.O_WRONLY |
|
|
7
7
|
constants.O_CREAT |
|
|
8
8
|
constants.O_EXCL |
|
|
@@ -16,7 +16,7 @@ export function acquirePrivateFileLock(path, description = 'Private storage') {
|
|
|
16
16
|
let handle;
|
|
17
17
|
try {
|
|
18
18
|
try {
|
|
19
|
-
handle =
|
|
19
|
+
handle = openLeaf(parent, CREATE_FLAGS, 0o600);
|
|
20
20
|
}
|
|
21
21
|
catch (error) {
|
|
22
22
|
if (errorCode(error) !== 'EEXIST')
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"safe-file.js","sourceRoot":"","sources":["../../../src/adapters/persistence/safe-file.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,SAAS,EAAE,SAAS,EAAE,
|
|
1
|
+
{"version":3,"file":"safe-file.js","sourceRoot":"","sources":["../../../src/adapters/persistence/safe-file.ts"],"names":[],"mappings":"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"}
|
|
@@ -5,11 +5,11 @@ export interface BoundSqliteDatabase {
|
|
|
5
5
|
readonly newDatabase: boolean;
|
|
6
6
|
}
|
|
7
7
|
/**
|
|
8
|
-
* Opens SQLite
|
|
8
|
+
* Opens SQLite from a safely validated database descriptor.
|
|
9
9
|
*
|
|
10
|
-
* The native driver only accepts a filename
|
|
11
|
-
*
|
|
12
|
-
* until the owning storage closes
|
|
10
|
+
* The native driver only accepts a filename. Linux reopens the descriptor.
|
|
11
|
+
* Darwin resolves the descriptor because SQLite needs a normal sidecar path.
|
|
12
|
+
* The validated descriptor remains open until the owning storage closes.
|
|
13
13
|
*/
|
|
14
14
|
export declare function openBoundSqliteDatabase(path: string, factory: SqliteDatabaseFactory, timeout: number): BoundSqliteDatabase;
|
|
15
15
|
export declare function closeBoundSqliteDatabase(bound: BoundSqliteDatabase): void;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"sqlite-bound-open.d.ts","sourceRoot":"","sources":["../../../src/adapters/storage/sqlite-bound-open.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"sqlite-bound-open.d.ts","sourceRoot":"","sources":["../../../src/adapters/storage/sqlite-bound-open.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,cAAc,EAAE,qBAAqB,EAAE,MAAM,oBAAoB,CAAA;AAG/E,MAAM,WAAW,mBAAmB;IAClC,QAAQ,CAAC,QAAQ,EAAE,cAAc,CAAA;IACjC,QAAQ,CAAC,cAAc,EAAE,MAAM,CAAA;IAC/B,QAAQ,CAAC,WAAW,EAAE,OAAO,CAAA;CAC9B;AA2GD;;;;;;GAMG;AACH,wBAAgB,uBAAuB,CACrC,IAAI,EAAE,MAAM,EACZ,OAAO,EAAE,qBAAqB,EAC9B,OAAO,EAAE,MAAM,GACd,mBAAmB,CAsErB;AAED,wBAAgB,wBAAwB,CAAC,KAAK,EAAE,mBAAmB,GAAG,IAAI,CAMzE;AAED,wBAAgB,sBAAsB,CACpC,QAAQ,EAAE,cAAc,EACxB,cAAc,EAAE,MAAM,GACrB,cAAc,CAahB"}
|
|
@@ -1,22 +1,46 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { closeSync, constants, fchmodSync, fstatSync, openSync, readdirSync } from 'node:fs';
|
|
2
2
|
import { basename, dirname, resolve } from 'node:path';
|
|
3
|
+
import { descriptorPath, openAt, unlinkAt } from '../persistence/posix-at.js';
|
|
3
4
|
import { StorageError } from './sqlite-errors.js';
|
|
4
5
|
const REQUIRED_PARENT_FLAGS = constants.O_DIRECTORY | (constants.O_NOFOLLOW ?? 0);
|
|
5
6
|
const REQUIRED_FILE_FLAGS = constants.O_RDWR | (constants.O_NOFOLLOW ?? 0);
|
|
6
7
|
function unsupported(message) {
|
|
7
8
|
return new StorageError('STORAGE_PATH_RACE_UNSUPPORTED', message);
|
|
8
9
|
}
|
|
9
|
-
function descriptorPath(fileDescriptor) {
|
|
10
|
-
if (process.platform === 'linux')
|
|
11
|
-
return `/proc/self/fd/${fileDescriptor}`;
|
|
12
|
-
if (process.platform === 'darwin' || process.platform === 'freebsd') {
|
|
13
|
-
return `/dev/fd/${fileDescriptor}`;
|
|
14
|
-
}
|
|
15
|
-
throw unsupported('This platform has no inode-bound SQLite descriptor path');
|
|
16
|
-
}
|
|
17
10
|
function sameInode(left, right) {
|
|
18
11
|
return left.dev === right.dev && left.ino === right.ino;
|
|
19
12
|
}
|
|
13
|
+
function liveFileDescriptors() {
|
|
14
|
+
const directory = process.platform === 'linux' ? '/proc/self/fd' : '/dev/fd';
|
|
15
|
+
const descriptors = new Set();
|
|
16
|
+
for (const name of readdirSync(directory)) {
|
|
17
|
+
if (!/^\d+$/u.test(name))
|
|
18
|
+
continue;
|
|
19
|
+
const descriptor = Number(name);
|
|
20
|
+
try {
|
|
21
|
+
fstatSync(descriptor);
|
|
22
|
+
descriptors.add(descriptor);
|
|
23
|
+
}
|
|
24
|
+
catch {
|
|
25
|
+
// readdir can expose its own descriptor after it closes.
|
|
26
|
+
}
|
|
27
|
+
}
|
|
28
|
+
return descriptors;
|
|
29
|
+
}
|
|
30
|
+
function assertDatabaseDescriptorIdentity(before, expected, path) {
|
|
31
|
+
for (const descriptor of liveFileDescriptors()) {
|
|
32
|
+
if (before.has(descriptor))
|
|
33
|
+
continue;
|
|
34
|
+
try {
|
|
35
|
+
if (sameInode(expected, fstatSync(descriptor)))
|
|
36
|
+
return;
|
|
37
|
+
}
|
|
38
|
+
catch {
|
|
39
|
+
// A concurrent close cannot establish the required identity.
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
throw new StorageError('STORAGE_PATH_RACE', `SQLite did not open the validated database file: ${path}`);
|
|
43
|
+
}
|
|
20
44
|
function assertOwnedDirectory(metadata, path) {
|
|
21
45
|
if (!metadata.isDirectory())
|
|
22
46
|
throw new StorageError('STORAGE_PATH', `Not a directory: ${path}`);
|
|
@@ -38,7 +62,7 @@ function openDirectoryChain(path) {
|
|
|
38
62
|
let descriptor = openSync('/', REQUIRED_PARENT_FLAGS);
|
|
39
63
|
try {
|
|
40
64
|
for (const component of resolve(path).split('/').filter(Boolean)) {
|
|
41
|
-
const next =
|
|
65
|
+
const next = openAt(descriptor, component, REQUIRED_PARENT_FLAGS);
|
|
42
66
|
closeSync(descriptor);
|
|
43
67
|
descriptor = next;
|
|
44
68
|
}
|
|
@@ -50,23 +74,26 @@ function openDirectoryChain(path) {
|
|
|
50
74
|
}
|
|
51
75
|
}
|
|
52
76
|
function openDatabaseFile(parentDescriptor, path) {
|
|
53
|
-
const
|
|
77
|
+
const name = basename(path);
|
|
54
78
|
const createFlags = REQUIRED_FILE_FLAGS | constants.O_CREAT | constants.O_EXCL;
|
|
55
79
|
try {
|
|
56
|
-
return { fileDescriptor:
|
|
80
|
+
return { fileDescriptor: openAt(parentDescriptor, name, createFlags, 0o600), newDatabase: true };
|
|
57
81
|
}
|
|
58
82
|
catch (error) {
|
|
59
83
|
if (error.code !== 'EEXIST')
|
|
60
84
|
throw error;
|
|
61
|
-
return {
|
|
85
|
+
return {
|
|
86
|
+
fileDescriptor: openAt(parentDescriptor, name, REQUIRED_FILE_FLAGS),
|
|
87
|
+
newDatabase: false,
|
|
88
|
+
};
|
|
62
89
|
}
|
|
63
90
|
}
|
|
64
91
|
/**
|
|
65
|
-
* Opens SQLite
|
|
92
|
+
* Opens SQLite from a safely validated database descriptor.
|
|
66
93
|
*
|
|
67
|
-
* The native driver only accepts a filename
|
|
68
|
-
*
|
|
69
|
-
* until the owning storage closes
|
|
94
|
+
* The native driver only accepts a filename. Linux reopens the descriptor.
|
|
95
|
+
* Darwin resolves the descriptor because SQLite needs a normal sidecar path.
|
|
96
|
+
* The validated descriptor remains open until the owning storage closes.
|
|
70
97
|
*/
|
|
71
98
|
export function openBoundSqliteDatabase(path, factory, timeout) {
|
|
72
99
|
if (process.platform === 'win32' ||
|
|
@@ -100,7 +127,9 @@ export function openBoundSqliteDatabase(path, factory, timeout) {
|
|
|
100
127
|
throw new StorageError('STORAGE_CORRUPT_EMPTY', `Existing SQLite path is empty: ${normalizedPath}`);
|
|
101
128
|
}
|
|
102
129
|
fchmodSync(fileDescriptor, 0o600);
|
|
130
|
+
const descriptorsBefore = liveFileDescriptors();
|
|
103
131
|
database = factory(descriptorPath(fileDescriptor), { timeout });
|
|
132
|
+
assertDatabaseDescriptorIdentity(descriptorsBefore, metadata, normalizedPath);
|
|
104
133
|
return { database, fileDescriptor, newDatabase: opened.newDatabase };
|
|
105
134
|
}
|
|
106
135
|
catch (error) {
|
|
@@ -114,11 +143,12 @@ export function openBoundSqliteDatabase(path, factory, timeout) {
|
|
|
114
143
|
closeSync(fileDescriptor);
|
|
115
144
|
if (created) {
|
|
116
145
|
try {
|
|
117
|
-
const
|
|
146
|
+
const name = basename(normalizedPath);
|
|
147
|
+
const currentDescriptor = openAt(parentDescriptor, name, REQUIRED_FILE_FLAGS);
|
|
118
148
|
try {
|
|
119
149
|
const current = fstatSync(currentDescriptor);
|
|
120
150
|
if (openedMetadata !== undefined && sameInode(openedMetadata, current))
|
|
121
|
-
|
|
151
|
+
unlinkAt(parentDescriptor, name);
|
|
122
152
|
}
|
|
123
153
|
finally {
|
|
124
154
|
closeSync(currentDescriptor);
|