@inlang/sdk 0.36.1 → 0.36.2
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/adapter/solidAdapter.d.ts.map +1 -1
- package/dist/createMessagesQuery.js +1 -1
- package/dist/createNewProject.d.ts.map +1 -1
- package/dist/createNewProject.js +19 -2
- package/dist/createNodeishFsWithWatcher.d.ts +1 -1
- package/dist/createNodeishFsWithWatcher.d.ts.map +1 -1
- package/dist/createNodeishFsWithWatcher.js +54 -45
- package/dist/createNodeishFsWithWatcher.test.js +1 -1
- package/dist/lint/message/lintMessages.d.ts.map +1 -1
- package/dist/lint/message/lintSingleMessage.d.ts.map +1 -1
- package/dist/listProjects.d.ts.map +1 -1
- package/dist/loadProject.d.ts.map +1 -1
- package/dist/loadProject.js +56 -50
- package/dist/loadProject.test.js +8 -13
- package/dist/migrations/maybeAddModuleCache.d.ts.map +1 -1
- package/dist/migrations/maybeAddModuleCache.js +24 -6
- package/dist/parseConfig.d.ts.map +1 -1
- package/dist/reactivity/map.d.ts +1 -0
- package/dist/reactivity/map.d.ts.map +1 -1
- package/dist/reactivity/solid.d.ts +11 -11
- package/dist/reactivity/solid.d.ts.map +1 -1
- package/dist/resolve-modules/cache.d.ts.map +1 -1
- package/dist/resolve-modules/cache.js +24 -16
- package/dist/resolve-modules/message-lint-rules/resolveMessageLintRules.d.ts +1 -1
- package/dist/resolve-modules/message-lint-rules/resolveMessageLintRules.d.ts.map +1 -1
- package/dist/resolve-modules/message-lint-rules/resolveMessageLintRules.js +1 -0
- package/dist/storage/helper.d.ts +1 -19
- package/dist/storage/helper.d.ts.map +1 -1
- package/dist/telemetry/capture.d.ts.map +1 -1
- package/dist/telemetry/groupIdentify.d.ts.map +1 -1
- package/dist/test-utilities/createMessage.d.ts.map +1 -1
- package/dist/v2/helper.d.ts +1 -89
- package/dist/v2/helper.d.ts.map +1 -1
- package/dist/validateProjectPath.d.ts +2 -8
- package/dist/validateProjectPath.d.ts.map +1 -1
- package/dist/validateProjectPath.js +0 -21
- package/dist/validateProjectPath.test.js +2 -18
- package/package.json +6 -6
- package/src/createMessagesQuery.ts +1 -1
- package/src/createNewProject.ts +19 -2
- package/src/createNodeishFsWithWatcher.test.ts +1 -1
- package/src/createNodeishFsWithWatcher.ts +53 -42
- package/src/loadProject.test.ts +11 -18
- package/src/loadProject.ts +69 -58
- package/src/migrations/maybeAddModuleCache.ts +21 -6
- package/src/persistence/filelock/acquireFileLock.ts +2 -2
- package/src/persistence/filelock/releaseLock.ts +1 -1
- package/src/resolve-modules/cache.ts +30 -14
- package/src/resolve-modules/message-lint-rules/resolveMessageLintRules.ts +1 -0
- package/src/validateProjectPath.test.ts +1 -19
- package/src/validateProjectPath.ts +4 -24
|
@@ -3,7 +3,7 @@ import { MessageLintRuleIsInvalidError } from "./errors.js";
|
|
|
3
3
|
export declare const resolveMessageLintRules: (args: {
|
|
4
4
|
messageLintRules: Array<MessageLintRule>;
|
|
5
5
|
}) => {
|
|
6
|
-
data: MessageLintRule
|
|
6
|
+
data: Array<MessageLintRule>;
|
|
7
7
|
errors: MessageLintRuleIsInvalidError[];
|
|
8
8
|
};
|
|
9
9
|
//# sourceMappingURL=resolveMessageLintRules.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"resolveMessageLintRules.d.ts","sourceRoot":"","sources":["../../../src/resolve-modules/message-lint-rules/resolveMessageLintRules.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,eAAe,EAAE,MAAM,2BAA2B,CAAA;AAC3D,OAAO,EAAE,6BAA6B,EAAE,MAAM,aAAa,CAAA;AAE3D,eAAO,MAAM,uBAAuB,SAAU;IAAE,gBAAgB,EAAE,
|
|
1
|
+
{"version":3,"file":"resolveMessageLintRules.d.ts","sourceRoot":"","sources":["../../../src/resolve-modules/message-lint-rules/resolveMessageLintRules.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,eAAe,EAAE,MAAM,2BAA2B,CAAA;AAC3D,OAAO,EAAE,6BAA6B,EAAE,MAAM,aAAa,CAAA;AAE3D,eAAO,MAAM,uBAAuB,SAAU;IAAE,gBAAgB,EAAE,KAAK,CAAC,eAAe,CAAC,CAAA;CAAE;UAE5E,KAAK,CAAC,eAAe,CAAC;YACpB,6BAA6B,EAAE;CAmB9C,CAAA"}
|
|
@@ -10,6 +10,7 @@ export const resolveMessageLintRules = (args) => {
|
|
|
10
10
|
if (Value.Check(MessageLintRule, rule) === false) {
|
|
11
11
|
const errors = [...Value.Errors(MessageLintRule, rule)];
|
|
12
12
|
result.errors.push(new MessageLintRuleIsInvalidError({
|
|
13
|
+
// @ts-ignore
|
|
13
14
|
id: rule.id,
|
|
14
15
|
errors,
|
|
15
16
|
}));
|
package/dist/storage/helper.d.ts
CHANGED
|
@@ -6,24 +6,6 @@ export declare function getPathFromMessageId(id: string): string;
|
|
|
6
6
|
* This produces a deterministic result when passed to stringify
|
|
7
7
|
* independent of the initialization order.
|
|
8
8
|
*/
|
|
9
|
-
export declare function normalizeMessage(message: Message):
|
|
10
|
-
id: string;
|
|
11
|
-
alias: Record<string, string>;
|
|
12
|
-
selectors: {
|
|
13
|
-
type: "VariableReference";
|
|
14
|
-
name: string;
|
|
15
|
-
}[];
|
|
16
|
-
variants: {
|
|
17
|
-
languageTag: string;
|
|
18
|
-
match: string[];
|
|
19
|
-
pattern: ({
|
|
20
|
-
type: "Text";
|
|
21
|
-
value: string;
|
|
22
|
-
} | {
|
|
23
|
-
type: "VariableReference";
|
|
24
|
-
name: string;
|
|
25
|
-
})[];
|
|
26
|
-
}[];
|
|
27
|
-
};
|
|
9
|
+
export declare function normalizeMessage(message: Message): Message;
|
|
28
10
|
export declare function stringifyMessage(message: Message): string;
|
|
29
11
|
//# sourceMappingURL=helper.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"helper.d.ts","sourceRoot":"","sources":["../../src/storage/helper.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAW,MAAM,2BAA2B,CAAA;AAI5D,wBAAgB,oBAAoB,CAAC,IAAI,EAAE,MAAM,sBAahD;AAED,wBAAgB,oBAAoB,CAAC,EAAE,EAAE,MAAM,UAG9C;AAED;;;;GAIG;AACH,wBAAgB,gBAAgB,CAAC,OAAO,EAAE,OAAO
|
|
1
|
+
{"version":3,"file":"helper.d.ts","sourceRoot":"","sources":["../../src/storage/helper.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAW,MAAM,2BAA2B,CAAA;AAI5D,wBAAgB,oBAAoB,CAAC,IAAI,EAAE,MAAM,sBAahD;AAED,wBAAgB,oBAAoB,CAAC,EAAE,EAAE,MAAM,UAG9C;AAED;;;;GAIG;AACH,wBAAgB,gBAAgB,CAAC,OAAO,EAAE,OAAO,GAuChB,OAAO,CACvC;AAED,wBAAgB,gBAAgB,CAAC,OAAO,EAAE,OAAO,UAEhD"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"capture.d.ts","sourceRoot":"","sources":["../../src/telemetry/capture.ts"],"names":[],"mappings":"AAEA;;;;;GAKG;AACH,QAAA,MAAM,MAAM,iCAAkC,CAAA;AAE9C;;;;GAIG;AACH,eAAO,MAAM,OAAO,UACZ,CAAC,
|
|
1
|
+
{"version":3,"file":"capture.d.ts","sourceRoot":"","sources":["../../src/telemetry/capture.ts"],"names":[],"mappings":"AAEA;;;;;GAKG;AACH,QAAA,MAAM,MAAM,iCAAkC,CAAA;AAE9C;;;;GAIG;AACH,eAAO,MAAM,OAAO,UACZ,CAAC,OAAO,MAAM,EAAE,MAAM,CAAC,QACxB;IACL,SAAS,EAAE,MAAM,CAAA;IACjB;;OAEG;IACH,UAAU,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,CAAA;CAC/B,kBAyBD,CAAA"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"groupIdentify.d.ts","sourceRoot":"","sources":["../../src/telemetry/groupIdentify.ts"],"names":[],"mappings":"AAEA;;;;GAIG;AACH,eAAO,MAAM,eAAe,SAAgB;IAC3C,SAAS,EAAE,MAAM,CAAA;IACjB;;OAEG;IACH,UAAU,EAAE,
|
|
1
|
+
{"version":3,"file":"groupIdentify.d.ts","sourceRoot":"","sources":["../../src/telemetry/groupIdentify.ts"],"names":[],"mappings":"AAEA;;;;GAIG;AACH,eAAO,MAAM,eAAe,SAAgB;IAC3C,SAAS,EAAE,MAAM,CAAA;IACjB;;OAEG;IACH,UAAU,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,CAAA;CAC/B,kBA2BA,CAAA"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"createMessage.d.ts","sourceRoot":"","sources":["../../src/test-utilities/createMessage.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAW,OAAO,EAAE,MAAM,iBAAiB,CAAA;AAEvD,eAAO,MAAM,aAAa,OAAQ,MAAM,YAAY,
|
|
1
|
+
{"version":3,"file":"createMessage.d.ts","sourceRoot":"","sources":["../../src/test-utilities/createMessage.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAW,OAAO,EAAE,MAAM,iBAAiB,CAAA;AAEvD,eAAO,MAAM,aAAa,OAAQ,MAAM,YAAY,MAAM,CAAC,MAAM,EAAE,OAAO,GAAG,MAAM,CAAC;;;;;;;;;;;;;;;CAkB/D,CAAA"}
|
package/dist/v2/helper.d.ts
CHANGED
|
@@ -35,95 +35,7 @@ export declare function addSlots(messageBundle: MessageBundle, locales: string[]
|
|
|
35
35
|
/**
|
|
36
36
|
* remove empty message slots without first creating a structured clone
|
|
37
37
|
*/
|
|
38
|
-
export declare function removeSlots(messageBundle: MessageBundleWithSlots):
|
|
39
|
-
id: string;
|
|
40
|
-
alias: Record<string, string>;
|
|
41
|
-
messages: {
|
|
42
|
-
selectors: {
|
|
43
|
-
annotation?: {
|
|
44
|
-
type: "function";
|
|
45
|
-
name: string;
|
|
46
|
-
options: {
|
|
47
|
-
name: string;
|
|
48
|
-
value: {
|
|
49
|
-
type: "literal";
|
|
50
|
-
value: string;
|
|
51
|
-
} | {
|
|
52
|
-
type: "variable";
|
|
53
|
-
name: string;
|
|
54
|
-
};
|
|
55
|
-
}[];
|
|
56
|
-
} | undefined;
|
|
57
|
-
type: "expression";
|
|
58
|
-
arg: {
|
|
59
|
-
type: "literal";
|
|
60
|
-
value: string;
|
|
61
|
-
} | {
|
|
62
|
-
type: "variable";
|
|
63
|
-
name: string;
|
|
64
|
-
};
|
|
65
|
-
}[];
|
|
66
|
-
variants: {
|
|
67
|
-
match: string[];
|
|
68
|
-
pattern: ({
|
|
69
|
-
type: "text";
|
|
70
|
-
value: string;
|
|
71
|
-
} | {
|
|
72
|
-
annotation?: {
|
|
73
|
-
type: "function";
|
|
74
|
-
name: string;
|
|
75
|
-
options: {
|
|
76
|
-
name: string;
|
|
77
|
-
value: {
|
|
78
|
-
type: "literal";
|
|
79
|
-
value: string;
|
|
80
|
-
} | {
|
|
81
|
-
type: "variable";
|
|
82
|
-
name: string;
|
|
83
|
-
};
|
|
84
|
-
}[];
|
|
85
|
-
} | undefined;
|
|
86
|
-
type: "expression";
|
|
87
|
-
arg: {
|
|
88
|
-
type: "literal";
|
|
89
|
-
value: string;
|
|
90
|
-
} | {
|
|
91
|
-
type: "variable";
|
|
92
|
-
name: string;
|
|
93
|
-
};
|
|
94
|
-
})[];
|
|
95
|
-
}[];
|
|
96
|
-
locale: string;
|
|
97
|
-
declarations: {
|
|
98
|
-
type: "input";
|
|
99
|
-
name: string;
|
|
100
|
-
value: {
|
|
101
|
-
annotation?: {
|
|
102
|
-
type: "function";
|
|
103
|
-
name: string;
|
|
104
|
-
options: {
|
|
105
|
-
name: string;
|
|
106
|
-
value: {
|
|
107
|
-
type: "literal";
|
|
108
|
-
value: string;
|
|
109
|
-
} | {
|
|
110
|
-
type: "variable";
|
|
111
|
-
name: string;
|
|
112
|
-
};
|
|
113
|
-
}[];
|
|
114
|
-
} | undefined;
|
|
115
|
-
type: "expression";
|
|
116
|
-
arg: {
|
|
117
|
-
type: "literal";
|
|
118
|
-
value: string;
|
|
119
|
-
} | {
|
|
120
|
-
type: "variable";
|
|
121
|
-
name: string;
|
|
122
|
-
};
|
|
123
|
-
};
|
|
124
|
-
}[];
|
|
125
|
-
}[];
|
|
126
|
-
};
|
|
38
|
+
export declare function removeSlots(messageBundle: MessageBundleWithSlots): MessageBundle;
|
|
127
39
|
/**
|
|
128
40
|
* Add newlines between bundles and messages to avoid merge conflicts
|
|
129
41
|
*/
|
package/dist/v2/helper.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"helper.d.ts","sourceRoot":"","sources":["../../src/v2/helper.ts"],"names":[],"mappings":"AAAA,OAAO,EACN,WAAW,EACX,aAAa,EACb,sBAAsB,EACtB,OAAO,EACP,WAAW,EACX,IAAI,EACJ,MAAM,YAAY,CAAA;AAEnB;;;;;;;;;GASG;AACH,wBAAgB,mBAAmB,CAAC,IAAI,EAAE;IACzC,EAAE,EAAE,MAAM,CAAA;IACV,QAAQ,EAAE,OAAO,EAAE,CAAA;IACnB,KAAK,CAAC,EAAE,aAAa,CAAC,OAAO,CAAC,CAAA;CAC9B,GAAG,aAAa,CAMhB;AAED;;;GAGG;AACH,wBAAgB,aAAa,CAAC,IAAI,EAAE;IACnC,MAAM,EAAE,WAAW,CAAA;IACnB,IAAI,EAAE,MAAM,CAAA;IACZ,KAAK,CAAC,EAAE,KAAK,CAAC,MAAM,CAAC,CAAA;CACrB,GAAG,OAAO,CAOV;AAED,wBAAgB,aAAa,CAAC,IAAI,EAAE,MAAM,GAAG,IAAI,CAKhD;AAMD;;GAEG;AACH,wBAAgB,iBAAiB,CAAC,MAAM,EAAE,WAAW,GAAG,WAAW,CAKlE;AAED;;GAEG;AACH,wBAAgB,QAAQ,CAAC,aAAa,EAAE,aAAa,EAAE,OAAO,EAAE,MAAM,EAAE,GAAG,sBAAsB,CAMhG;AAED;;GAEG;AACH,wBAAgB,WAAW,CAAC,aAAa,EAAE,sBAAsB
|
|
1
|
+
{"version":3,"file":"helper.d.ts","sourceRoot":"","sources":["../../src/v2/helper.ts"],"names":[],"mappings":"AAAA,OAAO,EACN,WAAW,EACX,aAAa,EACb,sBAAsB,EACtB,OAAO,EACP,WAAW,EACX,IAAI,EACJ,MAAM,YAAY,CAAA;AAEnB;;;;;;;;;GASG;AACH,wBAAgB,mBAAmB,CAAC,IAAI,EAAE;IACzC,EAAE,EAAE,MAAM,CAAA;IACV,QAAQ,EAAE,OAAO,EAAE,CAAA;IACnB,KAAK,CAAC,EAAE,aAAa,CAAC,OAAO,CAAC,CAAA;CAC9B,GAAG,aAAa,CAMhB;AAED;;;GAGG;AACH,wBAAgB,aAAa,CAAC,IAAI,EAAE;IACnC,MAAM,EAAE,WAAW,CAAA;IACnB,IAAI,EAAE,MAAM,CAAA;IACZ,KAAK,CAAC,EAAE,KAAK,CAAC,MAAM,CAAC,CAAA;CACrB,GAAG,OAAO,CAOV;AAED,wBAAgB,aAAa,CAAC,IAAI,EAAE,MAAM,GAAG,IAAI,CAKhD;AAMD;;GAEG;AACH,wBAAgB,iBAAiB,CAAC,MAAM,EAAE,WAAW,GAAG,WAAW,CAKlE;AAED;;GAEG;AACH,wBAAgB,QAAQ,CAAC,aAAa,EAAE,aAAa,EAAE,OAAO,EAAE,MAAM,EAAE,GAAG,sBAAsB,CAMhG;AAED;;GAEG;AACH,wBAAgB,WAAW,CAAC,aAAa,EAAE,sBAAsB,GAExC,aAAa,CACrC;AAED;;GAEG;AACH,wBAAgB,kBAAkB,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAMvD"}
|
|
@@ -1,23 +1,17 @@
|
|
|
1
|
-
import type { NodeishFilesystem } from "@lix-js/fs";
|
|
2
1
|
/**
|
|
3
2
|
* validate that a project path is absolute and ends with {name}.inlang.
|
|
4
3
|
*
|
|
5
4
|
* @throws if the path is not valid.
|
|
6
5
|
*/
|
|
7
|
-
export declare function assertValidProjectPath(projectPath: string):
|
|
6
|
+
export declare function assertValidProjectPath(projectPath: string): asserts projectPath is `${string}.inlang`;
|
|
8
7
|
/**
|
|
9
8
|
* tests whether a path ends with {name}.inlang
|
|
10
9
|
* (does not remove trailing slash)
|
|
11
10
|
*/
|
|
12
|
-
export declare function isInlangProjectPath(path: string):
|
|
11
|
+
export declare function isInlangProjectPath(path: string): path is `${string}.inlang`;
|
|
13
12
|
/**
|
|
14
13
|
* tests whether a path starts with a forward slash (/) or a windows-style
|
|
15
14
|
* drive letter (C: or D:, etc.) followed by a slash
|
|
16
15
|
*/
|
|
17
16
|
export declare function isAbsolutePath(path: string): boolean;
|
|
18
|
-
/**
|
|
19
|
-
* Returns true if the path exists (file or directory), false otherwise.
|
|
20
|
-
*
|
|
21
|
-
*/
|
|
22
|
-
export declare function pathExists(filePath: string, nodeishFs: NodeishFilesystem): Promise<boolean>;
|
|
23
17
|
//# sourceMappingURL=validateProjectPath.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"validateProjectPath.d.ts","sourceRoot":"","sources":["../src/validateProjectPath.ts"],"names":[],"mappings":"AAAA,
|
|
1
|
+
{"version":3,"file":"validateProjectPath.d.ts","sourceRoot":"","sources":["../src/validateProjectPath.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AACH,wBAAgB,sBAAsB,CACrC,WAAW,EAAE,MAAM,GACjB,OAAO,CAAC,WAAW,IAAI,GAAG,MAAM,SAAS,CAS3C;AAED;;;GAGG;AACH,wBAAgB,mBAAmB,CAAC,IAAI,EAAE,MAAM,GAAG,IAAI,IAAI,GAAG,MAAM,SAAS,CAE5E;AAED;;;GAGG;AACH,wBAAgB,cAAc,CAAC,IAAI,EAAE,MAAM,WAO1C"}
|
|
@@ -29,24 +29,3 @@ export function isAbsolutePath(path) {
|
|
|
29
29
|
// /^(?:[A-Za-z]:\\(?:[^\\]+\\)*[^\\]+|[A-Za-z]:\/(?:[^/]+\/)*[^/]+|\/(?:[^/]+\/)*[^/]+)$/
|
|
30
30
|
// return matchPosixAndWindowsAbsolutePaths.test(path)
|
|
31
31
|
}
|
|
32
|
-
/**
|
|
33
|
-
* Returns true if the path exists (file or directory), false otherwise.
|
|
34
|
-
*
|
|
35
|
-
*/
|
|
36
|
-
export async function pathExists(filePath, nodeishFs) {
|
|
37
|
-
// from paraglide-js/src/services/file-handling/exists.ts
|
|
38
|
-
// TODO: add fs.exists to @lix-js/fs
|
|
39
|
-
try {
|
|
40
|
-
await nodeishFs.stat(filePath);
|
|
41
|
-
return true;
|
|
42
|
-
}
|
|
43
|
-
catch (error) {
|
|
44
|
-
//@ts-ignore
|
|
45
|
-
if (error.code === "ENOENT") {
|
|
46
|
-
return false;
|
|
47
|
-
}
|
|
48
|
-
else {
|
|
49
|
-
throw new Error(`Failed to check if path exists: ${error}`, { cause: error });
|
|
50
|
-
}
|
|
51
|
-
}
|
|
52
|
-
}
|
|
@@ -1,6 +1,5 @@
|
|
|
1
|
-
import { assert, describe,
|
|
2
|
-
import { assertValidProjectPath, isAbsolutePath, isInlangProjectPath,
|
|
3
|
-
import { mockRepo } from "@lix-js/client";
|
|
1
|
+
import { assert, describe, it } from "vitest";
|
|
2
|
+
import { assertValidProjectPath, isAbsolutePath, isInlangProjectPath, } from "./validateProjectPath.js";
|
|
4
3
|
describe("isAbsolutePath", () => {
|
|
5
4
|
it("should correctly identify Unix absolute paths", () => {
|
|
6
5
|
assert.isTrue(isAbsolutePath("/home/user/documents/file.txt"));
|
|
@@ -39,18 +38,3 @@ describe("assertValidProjectPath", () => {
|
|
|
39
38
|
assert.throws(() => assertValidProjectPath("/path/to/green-elephant.inlang/settings.json"));
|
|
40
39
|
});
|
|
41
40
|
});
|
|
42
|
-
// moar tests in paraglide-js/src/services/file-handling/exists.test.ts
|
|
43
|
-
describe("pathExists", () => {
|
|
44
|
-
it("should work for files", async () => {
|
|
45
|
-
const repo = await mockRepo();
|
|
46
|
-
await repo.nodeishFs.writeFile("/test.txt", "hello");
|
|
47
|
-
expect(await pathExists("/test.txt", repo.nodeishFs)).toBe(true);
|
|
48
|
-
expect(await pathExists("/does-not-exist.txt", repo.nodeishFs)).toBe(false);
|
|
49
|
-
});
|
|
50
|
-
it("should work for directories", async () => {
|
|
51
|
-
const repo = await mockRepo();
|
|
52
|
-
await repo.nodeishFs.mkdir("/test/project.inlang", { recursive: true });
|
|
53
|
-
expect(await pathExists("/test/project.inlang", repo.nodeishFs)).toBe(true);
|
|
54
|
-
expect(await pathExists("/test/white-gorilla.inlang", repo.nodeishFs)).toBe(false);
|
|
55
|
-
});
|
|
56
|
-
});
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@inlang/sdk",
|
|
3
3
|
"type": "module",
|
|
4
|
-
"version": "0.36.
|
|
4
|
+
"version": "0.36.2",
|
|
5
5
|
"license": "Apache-2.0",
|
|
6
6
|
"publishConfig": {
|
|
7
7
|
"access": "public"
|
|
@@ -37,14 +37,14 @@
|
|
|
37
37
|
"@inlang/json-types": "1.1.0",
|
|
38
38
|
"@inlang/language-tag": "1.5.1",
|
|
39
39
|
"@inlang/message": "2.1.0",
|
|
40
|
-
"@inlang/module": "1.2.13",
|
|
41
40
|
"@inlang/message-lint-rule": "1.4.7",
|
|
42
41
|
"@inlang/plugin": "2.4.13",
|
|
42
|
+
"@inlang/module": "1.2.13",
|
|
43
43
|
"@inlang/project-settings": "2.4.2",
|
|
44
|
-
"@lix-js/client": "2.2.0",
|
|
45
|
-
"@lix-js/fs": "2.1.0",
|
|
46
44
|
"@inlang/result": "1.1.0",
|
|
47
|
-
"@inlang/translatable": "1.3.1"
|
|
45
|
+
"@inlang/translatable": "1.3.1",
|
|
46
|
+
"@lix-js/fs": "2.1.0",
|
|
47
|
+
"@lix-js/client": "2.2.0"
|
|
48
48
|
},
|
|
49
49
|
"devDependencies": {
|
|
50
50
|
"@types/debug": "^4.1.12",
|
|
@@ -54,7 +54,7 @@
|
|
|
54
54
|
"jsdom": "22.1.0",
|
|
55
55
|
"patch-package": "6.5.1",
|
|
56
56
|
"tsd": "^0.25.0",
|
|
57
|
-
"typescript": "5.
|
|
57
|
+
"typescript": "^5.5.2",
|
|
58
58
|
"vitest": "^0.33.0"
|
|
59
59
|
},
|
|
60
60
|
"scripts": {
|
|
@@ -107,7 +107,7 @@ export function createMessagesQuery({
|
|
|
107
107
|
nodeishFs: nodeishFs,
|
|
108
108
|
// this message is called whenever a file changes that was read earlier by this filesystem
|
|
109
109
|
// - the plugin loads messages -> reads the file messages.json -> start watching on messages.json -> updateMessages
|
|
110
|
-
|
|
110
|
+
onChange: () => {
|
|
111
111
|
// reload
|
|
112
112
|
loadMessagesViaPlugin(
|
|
113
113
|
fsWithWatcher,
|
package/src/createNewProject.ts
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import type { Repository } from "@lix-js/client"
|
|
2
|
+
import type { NodeishFilesystem } from "@lix-js/fs"
|
|
2
3
|
import { ProjectSettings } from "@inlang/project-settings"
|
|
3
|
-
import { assertValidProjectPath
|
|
4
|
+
import { assertValidProjectPath } from "./validateProjectPath.js"
|
|
4
5
|
import { defaultProjectSettings } from "./defaultProjectSettings.js"
|
|
5
6
|
|
|
6
7
|
/**
|
|
@@ -15,7 +16,7 @@ export async function createNewProject(args: {
|
|
|
15
16
|
assertValidProjectPath(args.projectPath)
|
|
16
17
|
|
|
17
18
|
const nodeishFs = args.repo.nodeishFs
|
|
18
|
-
if (await
|
|
19
|
+
if (await directoryExists(args.projectPath, nodeishFs)) {
|
|
19
20
|
throw new Error(`projectPath already exists, received "${args.projectPath}"`)
|
|
20
21
|
}
|
|
21
22
|
const settingsText = JSON.stringify(args.projectSettings ?? defaultProjectSettings, undefined, 2)
|
|
@@ -27,3 +28,19 @@ export async function createNewProject(args: {
|
|
|
27
28
|
nodeishFs.mkdir(`${args.projectPath}/cache/modules`, { recursive: true }),
|
|
28
29
|
])
|
|
29
30
|
}
|
|
31
|
+
|
|
32
|
+
/**
|
|
33
|
+
* Returns true if the path exists (file or directory), false otherwise.
|
|
34
|
+
*/
|
|
35
|
+
async function directoryExists(filePath: string, nodeishFs: NodeishFilesystem) {
|
|
36
|
+
try {
|
|
37
|
+
const stat = await nodeishFs.stat(filePath)
|
|
38
|
+
return stat.isDirectory()
|
|
39
|
+
} catch (error: any) {
|
|
40
|
+
if (error && "code" in error && error.code === "ENOENT") {
|
|
41
|
+
return false
|
|
42
|
+
} else {
|
|
43
|
+
throw new Error(`Failed to check if path exists: ${error}`, { cause: error })
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
}
|
|
@@ -8,67 +8,78 @@ import type { NodeishFilesystem } from "@lix-js/fs"
|
|
|
8
8
|
*/
|
|
9
9
|
export const createNodeishFsWithWatcher = (args: {
|
|
10
10
|
nodeishFs: NodeishFilesystem
|
|
11
|
-
|
|
11
|
+
onChange: () => void
|
|
12
12
|
}): NodeishFilesystem & {
|
|
13
13
|
stopWatching: () => void
|
|
14
14
|
} => {
|
|
15
|
-
const pathList
|
|
16
|
-
|
|
15
|
+
const pathList = new Set<string>()
|
|
16
|
+
const abortControllers = new Set<AbortController>()
|
|
17
17
|
|
|
18
18
|
const stopWatching = () => {
|
|
19
19
|
for (const ac of abortControllers) {
|
|
20
20
|
ac.abort()
|
|
21
|
+
abortControllers.delete(ac) // release reference
|
|
21
22
|
}
|
|
22
|
-
// release references
|
|
23
|
-
abortControllers = []
|
|
24
23
|
}
|
|
25
24
|
|
|
26
|
-
const makeWatcher = (path: string) => {
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
25
|
+
const makeWatcher = async (path: string) => {
|
|
26
|
+
try {
|
|
27
|
+
const ac = new AbortController()
|
|
28
|
+
abortControllers.add(ac)
|
|
29
|
+
const watcher = args.nodeishFs.watch(path, {
|
|
30
|
+
signal: ac.signal,
|
|
31
|
+
recursive: true,
|
|
32
|
+
persistent: false,
|
|
33
|
+
})
|
|
34
|
+
if (watcher) {
|
|
35
|
+
//eslint-disable-next-line @typescript-eslint/no-unused-vars
|
|
36
|
+
for await (const event of watcher) {
|
|
37
|
+
// whenever the watcher changes we need to update the messages
|
|
38
|
+
args.onChange()
|
|
40
39
|
}
|
|
41
|
-
} catch (err: any) {
|
|
42
|
-
if (err.name === "AbortError") return
|
|
43
|
-
// https://github.com/opral/monorepo/issues/1647
|
|
44
|
-
// the file does not exist (yet)
|
|
45
|
-
// this is not testable beacause the fs.watch api differs
|
|
46
|
-
// from node and lix. lenghty
|
|
47
|
-
else if (err.code === "ENOENT") return
|
|
48
|
-
throw err
|
|
49
40
|
}
|
|
50
|
-
}
|
|
41
|
+
} catch (err: any) {
|
|
42
|
+
if (err.name === "AbortError") return
|
|
43
|
+
// https://github.com/opral/monorepo/issues/1647
|
|
44
|
+
// the file does not exist (yet)
|
|
45
|
+
// this is not testable beacause the fs.watch api differs
|
|
46
|
+
// from node and lix. lenghty
|
|
47
|
+
else if (err.code === "ENOENT") return
|
|
48
|
+
throw err
|
|
49
|
+
}
|
|
51
50
|
}
|
|
52
51
|
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
52
|
+
/**
|
|
53
|
+
* Creates watchers on-the-fly for any file or directory that is not yet watched.
|
|
54
|
+
*
|
|
55
|
+
* We do this instead of recursively watching the entire project because fs.watch does not support
|
|
56
|
+
* recursive watching on linux in node 18. Once node 18 support is dropped this can be drastically simplified.
|
|
57
|
+
*/
|
|
58
|
+
const watched = <T extends any[], R>(
|
|
59
|
+
fn: (path: string, ...rest: T) => R
|
|
60
|
+
): ((path: string, ...rest: T) => R) => {
|
|
61
|
+
return (path: string, ...rest: T): R => {
|
|
62
|
+
if (!pathList.has(path)) {
|
|
63
|
+
makeWatcher(path)
|
|
64
|
+
pathList.add(path)
|
|
65
|
+
}
|
|
66
|
+
return fn(path, ...rest)
|
|
57
67
|
}
|
|
58
|
-
return args.nodeishFs.readFile(path, options)
|
|
59
68
|
}
|
|
60
69
|
|
|
61
70
|
return {
|
|
71
|
+
...args.nodeishFs,
|
|
72
|
+
/**
|
|
73
|
+
* Reads the file and automatically adds it to the list of watched files.
|
|
74
|
+
* Any changes to the file will trigger a message update.
|
|
75
|
+
*/
|
|
62
76
|
// @ts-expect-error
|
|
63
|
-
readFile: (
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
writeFile: args.nodeishFs.writeFile,
|
|
70
|
-
watch: args.nodeishFs.watch,
|
|
71
|
-
stat: args.nodeishFs.stat,
|
|
77
|
+
readFile: watched(args.nodeishFs.readFile),
|
|
78
|
+
/**
|
|
79
|
+
* Reads the directory and automatically adds it to the list of watched files.
|
|
80
|
+
* Any changes to the directory will trigger a message update.
|
|
81
|
+
*/
|
|
82
|
+
readdir: watched(args.nodeishFs.readdir),
|
|
72
83
|
stopWatching,
|
|
73
84
|
}
|
|
74
85
|
}
|
package/src/loadProject.test.ts
CHANGED
|
@@ -278,26 +278,19 @@ describe("initialization", () => {
|
|
|
278
278
|
expect(result.data).toBeDefined()
|
|
279
279
|
})
|
|
280
280
|
|
|
281
|
-
|
|
282
|
-
// https://github.com/opral/inlang-message-sdk/issues/76
|
|
283
|
-
// it doesn't work because failure to open the settings file doesn't throw
|
|
284
|
-
// errors are returned in project.errors()
|
|
285
|
-
it("should resolve from a windows path", async () => {
|
|
281
|
+
it.skipIf(() => process.platform !== "win32")("should resolve from a windows path", async () => {
|
|
286
282
|
const repo = await mockRepo()
|
|
287
283
|
const fs = repo.nodeishFs
|
|
288
284
|
await fs.mkdir("C:\\Users\\user\\project.inlang", { recursive: true })
|
|
289
285
|
await fs.writeFile("C:\\Users\\user\\project.inlang\\settings.json", JSON.stringify(settings))
|
|
290
286
|
|
|
291
|
-
const
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
})
|
|
297
|
-
)
|
|
287
|
+
const project = await loadProject({
|
|
288
|
+
projectPath: "C:\\Users\\user\\project.inlang",
|
|
289
|
+
repo,
|
|
290
|
+
_import,
|
|
291
|
+
})
|
|
298
292
|
|
|
299
|
-
expect(
|
|
300
|
-
expect(result.data).toBeDefined()
|
|
293
|
+
expect(project.errors()).toEqual([])
|
|
301
294
|
})
|
|
302
295
|
|
|
303
296
|
describe("settings", () => {
|
|
@@ -362,9 +355,9 @@ describe("initialization", () => {
|
|
|
362
355
|
it("should not re-write the settings to disk when initializing", async () => {
|
|
363
356
|
const repo = await mockRepo()
|
|
364
357
|
const fs = repo.nodeishFs
|
|
365
|
-
const
|
|
358
|
+
const settingsWithDifferentFormatting = JSON.stringify(settings, undefined, 4)
|
|
366
359
|
await fs.mkdir("/user/project.inlang", { recursive: true })
|
|
367
|
-
await fs.writeFile("/user/project.inlang/settings.json",
|
|
360
|
+
await fs.writeFile("/user/project.inlang/settings.json", settingsWithDifferentFormatting)
|
|
368
361
|
|
|
369
362
|
const project = await loadProject({
|
|
370
363
|
projectPath: "/user/project.inlang",
|
|
@@ -375,7 +368,7 @@ describe("initialization", () => {
|
|
|
375
368
|
const settingsOnDisk = await fs.readFile("/user/project.inlang/settings.json", {
|
|
376
369
|
encoding: "utf-8",
|
|
377
370
|
})
|
|
378
|
-
expect(settingsOnDisk).toBe(
|
|
371
|
+
expect(settingsOnDisk).toBe(settingsWithDifferentFormatting)
|
|
379
372
|
|
|
380
373
|
project.setSettings(project.settings())
|
|
381
374
|
// TODO: how can we await `setsettings` correctly
|
|
@@ -384,7 +377,7 @@ describe("initialization", () => {
|
|
|
384
377
|
const newsettingsOnDisk = await fs.readFile("/user/project.inlang/settings.json", {
|
|
385
378
|
encoding: "utf-8",
|
|
386
379
|
})
|
|
387
|
-
expect(newsettingsOnDisk).not.toBe(
|
|
380
|
+
expect(newsettingsOnDisk).not.toBe(settingsWithDifferentFormatting)
|
|
388
381
|
})
|
|
389
382
|
})
|
|
390
383
|
|