@decohere/workspace 0.0.1-dev.126 → 0.0.1-dev.5

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.
Files changed (76) hide show
  1. package/README.md +1 -1
  2. package/package.json +3 -13
  3. package/src/const.ts +19 -0
  4. package/src/errors.ts +1 -0
  5. package/src/factories/config.factory.ts +21 -0
  6. package/src/factories/find-workspace-root.ts +32 -0
  7. package/src/factories/project.factory.ts +75 -0
  8. package/src/factories/workspace.factory.ts +44 -0
  9. package/{types/src/index.d.ts → src/index.ts} +7 -1
  10. package/src/models/has-package-json.mixin.ts +30 -0
  11. package/src/models/has-tsconfig.mixin.ts +48 -0
  12. package/src/models/package-aliases.ts +130 -0
  13. package/src/models/package-json.model.ts +231 -0
  14. package/src/models/project-file-event.ts +9 -0
  15. package/src/models/project.model.ts +340 -0
  16. package/src/models/source-extensions.ts +59 -0
  17. package/src/models/tsconfig.model.ts +81 -0
  18. package/src/models/workspace-config.type.ts +57 -0
  19. package/src/models/workspace.model.ts +178 -0
  20. package/tests/find-workspace-root.spec.ts +30 -0
  21. package/tests/package-aliases.spec.ts +160 -0
  22. package/tests/package-json.model.spec.ts +78 -0
  23. package/tests/project.factory.spec.ts +100 -0
  24. package/tests/source-extensions.spec.ts +33 -0
  25. package/tests/workspace.factory.spec.ts +147 -0
  26. package/LICENSE +0 -15
  27. package/commonjs/src/const.js +0 -69
  28. package/commonjs/src/errors.js +0 -12
  29. package/commonjs/src/factories/config.factory.js +0 -90
  30. package/commonjs/src/factories/find-workspace-root.js +0 -37
  31. package/commonjs/src/factories/project.factory.js +0 -73
  32. package/commonjs/src/factories/workspace.factory.js +0 -50
  33. package/commonjs/src/index.js +0 -74
  34. package/commonjs/src/models/has-package-json.mixin.js +0 -50
  35. package/commonjs/src/models/has-tsconfig.mixin.js +0 -75
  36. package/commonjs/src/models/package-aliases.js +0 -112
  37. package/commonjs/src/models/package-json.model.js +0 -202
  38. package/commonjs/src/models/project-file-event.js +0 -4
  39. package/commonjs/src/models/project.model.js +0 -316
  40. package/commonjs/src/models/source-extensions.js +0 -81
  41. package/commonjs/src/models/tsconfig.model.js +0 -97
  42. package/commonjs/src/models/workspace-config.type.js +0 -7
  43. package/commonjs/src/models/workspace.model.js +0 -153
  44. package/es6/src/const.js +0 -36
  45. package/es6/src/errors.js +0 -2
  46. package/es6/src/factories/config.factory.js +0 -34
  47. package/es6/src/factories/find-workspace-root.js +0 -26
  48. package/es6/src/factories/project.factory.js +0 -58
  49. package/es6/src/factories/workspace.factory.js +0 -35
  50. package/es6/src/index.js +0 -14
  51. package/es6/src/models/has-package-json.mixin.js +0 -35
  52. package/es6/src/models/has-tsconfig.mixin.js +0 -60
  53. package/es6/src/models/package-aliases.js +0 -97
  54. package/es6/src/models/package-json.model.js +0 -192
  55. package/es6/src/models/project-file-event.js +0 -1
  56. package/es6/src/models/project.model.js +0 -301
  57. package/es6/src/models/source-extensions.js +0 -66
  58. package/es6/src/models/tsconfig.model.js +0 -74
  59. package/es6/src/models/workspace-config.type.js +0 -4
  60. package/es6/src/models/workspace.model.js +0 -143
  61. package/types/src/const.d.ts +0 -8
  62. package/types/src/errors.d.ts +0 -2
  63. package/types/src/factories/config.factory.d.ts +0 -6
  64. package/types/src/factories/find-workspace-root.d.ts +0 -6
  65. package/types/src/factories/project.factory.d.ts +0 -8
  66. package/types/src/factories/workspace.factory.d.ts +0 -9
  67. package/types/src/models/has-package-json.mixin.d.ts +0 -9
  68. package/types/src/models/has-tsconfig.mixin.d.ts +0 -11
  69. package/types/src/models/package-aliases.d.ts +0 -28
  70. package/types/src/models/package-json.model.d.ts +0 -40
  71. package/types/src/models/project-file-event.d.ts +0 -9
  72. package/types/src/models/project.model.d.ts +0 -64
  73. package/types/src/models/source-extensions.d.ts +0 -22
  74. package/types/src/models/tsconfig.model.d.ts +0 -11
  75. package/types/src/models/workspace-config.type.d.ts +0 -52
  76. package/types/src/models/workspace.model.d.ts +0 -40
@@ -1,316 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", {
3
- value: true
4
- });
5
- Object.defineProperty(exports, "Project", {
6
- enumerable: true,
7
- get: function() {
8
- return Project;
9
- }
10
- });
11
- const _nodefs = require("node:fs");
12
- const _nodepath = /*#__PURE__*/ _interop_require_default(require("node:path"));
13
- const _caching = require("@decohere/core/caching");
14
- const _extensibility = require("@decohere/core/extensibility");
15
- const _io = require("@decohere/devkit/io");
16
- const _picomatch = /*#__PURE__*/ _interop_require_default(require("picomatch"));
17
- const _rxjs = require("rxjs");
18
- const _errors = require("../errors.js");
19
- const _haspackagejsonmixin = require("./has-package-json.mixin.js");
20
- const _hastsconfigmixin = require("./has-tsconfig.mixin.js");
21
- const _packagejsonmodel = require("./package-json.model.js");
22
- const _sourceextensions = require("./source-extensions.js");
23
- function _interop_require_default(obj) {
24
- return obj && obj.__esModule ? obj : {
25
- default: obj
26
- };
27
- }
28
- function _ts_decorate(decorators, target, key, desc) {
29
- var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
30
- if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
31
- else for(var i = decorators.length - 1; i >= 0; i--)if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
32
- return c > 3 && r && Object.defineProperty(target, key, r), r;
33
- }
34
- function _ts_metadata(k, v) {
35
- if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
36
- }
37
- class Project extends (0, _extensibility.mixwith)(_haspackagejsonmixin.HasPackageJson, _hastsconfigmixin.HasTsConfig) {
38
- packageJson;
39
- #projectFileChangedSubject = new _rxjs.Subject();
40
- #sourceFiles = new Map();
41
- #projectConfig;
42
- #name;
43
- #projectDirectory;
44
- #selectedConfiguration;
45
- #hasLoadedSourceFiles = false;
46
- #watcher;
47
- constructor(name, config = {}, selectedConfigurationName){
48
- super();
49
- this.#name = name;
50
- this.#projectDirectory = config?.projectDir ?? name;
51
- this.#projectConfig = config;
52
- this.#selectedConfiguration = this.resolveConfiguration(selectedConfigurationName);
53
- this.packageJson = config.packageJson ?? new _packagejsonmodel.PackageJson();
54
- }
55
- get name() {
56
- return this.#name;
57
- }
58
- get isPrivate() {
59
- return this.packageJson?.private === true;
60
- }
61
- toString() {
62
- return `Project(${this.#name})`;
63
- }
64
- get projectDirectory() {
65
- return this.#projectDirectory;
66
- }
67
- get projectRoot() {
68
- return _nodepath.default.resolve(this.#projectConfig.rootDir ?? "./", this.#projectDirectory);
69
- }
70
- get configuration() {
71
- return this.#selectedConfiguration;
72
- }
73
- get packageJsonDirectory() {
74
- return this.#absoluteProjectDir;
75
- }
76
- get tsConfigDirectory() {
77
- return this.#absoluteProjectDir;
78
- }
79
- get fallbackTsConfigDirectory() {
80
- return this.#projectConfig.rootDir;
81
- }
82
- get rootDir() {
83
- return this.#projectConfig.rootDir ?? "./";
84
- }
85
- get #absoluteProjectDir() {
86
- return this.projectRoot;
87
- }
88
- get include() {
89
- return this.#selectedConfiguration.include ?? this.#projectConfig.include ?? [];
90
- }
91
- get ignore() {
92
- const baseIgnore = this.#projectConfig.ignore ?? [];
93
- const selectedIgnore = this.#selectedConfiguration.ignore ?? [];
94
- return [
95
- ...baseIgnore,
96
- ...selectedIgnore
97
- ];
98
- }
99
- get copyFiles() {
100
- const base = this.#projectConfig.copyFiles ?? [];
101
- const selected = this.#selectedConfiguration.copyFiles ?? [];
102
- return [
103
- ...base,
104
- ...selected
105
- ];
106
- }
107
- get dockerConfig() {
108
- return this.#projectConfig.docker;
109
- }
110
- get uiConfig() {
111
- return this.#projectConfig.ui;
112
- }
113
- get configurations() {
114
- return this.#projectConfig.configurations ?? [];
115
- }
116
- get projectFileChanged$() {
117
- return this.#projectFileChangedSubject.asObservable();
118
- }
119
- async getAllFiles() {
120
- const files = await (0, _io.findFiles)(this.include, {
121
- cwd: this.#absoluteProjectDir,
122
- ignore: this.ignore
123
- });
124
- this.#sourceFiles.clear();
125
- for (const file of files){
126
- this.#sourceFiles.set(file.relativePath, file);
127
- }
128
- this.#hasLoadedSourceFiles = true;
129
- return files;
130
- }
131
- isSourceFile(file) {
132
- return this.#sourceFiles.has(file.relativePath);
133
- }
134
- async watch(configuration) {
135
- if (this.#watcher != null) {
136
- return this.#watcher;
137
- }
138
- if (!this.#hasLoadedSourceFiles) {
139
- await this.getAllFiles();
140
- }
141
- const watcher = (0, _io.watch)(this.#absoluteProjectDir, {
142
- ignoreInitial: true
143
- });
144
- this.#watcher = watcher;
145
- watcher.on(_io.WatchEvents.add, (file)=>{
146
- const fileEx = file;
147
- this.updateSourceFileCache(_io.WatchEvents.add, fileEx);
148
- this.#projectFileChangedSubject.next({
149
- project: this,
150
- configuration,
151
- eventName: _io.WatchEvents.add,
152
- file: fileEx
153
- });
154
- });
155
- watcher.on(_io.WatchEvents.change, (file)=>{
156
- const fileEx = file;
157
- this.updateSourceFileCache(_io.WatchEvents.change, fileEx);
158
- this.#projectFileChangedSubject.next({
159
- project: this,
160
- configuration,
161
- eventName: _io.WatchEvents.change,
162
- file: fileEx
163
- });
164
- });
165
- watcher.on(_io.WatchEvents.unlink, (file)=>{
166
- const fileEx = file;
167
- this.updateSourceFileCache(_io.WatchEvents.unlink, fileEx);
168
- this.#projectFileChangedSubject.next({
169
- project: this,
170
- configuration,
171
- eventName: _io.WatchEvents.unlink,
172
- file: fileEx
173
- });
174
- });
175
- return watcher;
176
- }
177
- stopWatching() {
178
- this.#watcher?.close();
179
- this.#watcher = undefined;
180
- }
181
- getRootOut() {
182
- return _nodepath.default.join(this.getWorkspaceOut(), this.#selectedConfiguration.name);
183
- }
184
- getOutDir(target = "") {
185
- const targetDir = this.#selectedConfiguration.pack ? _nodepath.default.join(this.projectDirectory, target) : _nodepath.default.join(this.projectDirectory);
186
- const out = _nodepath.default.join(this.getRootOut(), targetDir);
187
- return out;
188
- }
189
- getConfiguration(name) {
190
- return this.configurations.find((b)=>b.name === name);
191
- }
192
- /**
193
- * The package's entry source file. A TypeScript `main` (the workspace convention,
194
- * `src/index.ts`) is used as written. A `main` or `exports["."]` that describes the published
195
- * layout (`index.js`, `./es6/src/index.js`) is mapped back to the source it was built from,
196
- * falling back to `src/index.ts`.
197
- */ getSourceEntryPath() {
198
- const projectRoot = _nodepath.default.join(this.rootDir, this.projectDirectory);
199
- const main = this.packageJson?.main;
200
- if (main != null && _sourceextensions.sourceExtensions.isSource(main)) {
201
- return _nodepath.default.join(projectRoot, main);
202
- }
203
- const exports1 = this.packageJson?.exports;
204
- const root = exports1 == null ? undefined : typeof exports1 === "string" ? exports1 : exports1["."] ?? (Object.keys(exports1).some((k)=>k.startsWith(".")) ? undefined : exports1);
205
- for (const built of [
206
- root == null ? undefined : firstExportTarget(root),
207
- main
208
- ]){
209
- const fromSrc = built?.match(/(?:^|\/)(src\/.+)$/)?.[1];
210
- const source = fromSrc == null ? undefined : sourceFileFor(_nodepath.default.join(projectRoot, fromSrc));
211
- if (source != null) return source;
212
- }
213
- const conventional = _nodepath.default.join(projectRoot, "src/index.ts");
214
- if (main == null || (0, _nodefs.existsSync)(conventional)) return conventional;
215
- return _nodepath.default.join(projectRoot, main);
216
- }
217
- /**
218
- * The source file each subpath in package.json `exports` names, such as `./auth` →
219
- * `<project>/src/auth/auth.extensions.ts`. Exports point at the release layout
220
- * (`./es6/src/auth/auth.extensions.js`); the source is the part from `src/`, with its
221
- * TypeScript extension. Wildcard subpaths, and targets with no such source file, are left out.
222
- */ getSourceExports() {
223
- const exports1 = this.packageJson?.exports;
224
- if (exports1 == null || typeof exports1 === "string") return {};
225
- const projectRoot = _nodepath.default.join(this.rootDir, this.projectDirectory);
226
- const sources = {};
227
- for (const [subpath, target] of Object.entries(exports1)){
228
- if (!subpath.startsWith("./") || subpath.includes("*")) continue;
229
- const built = firstExportTarget(target);
230
- const fromSrc = built?.match(/(?:^|\/)(src\/.+)$/)?.[1];
231
- if (fromSrc == null) continue;
232
- const source = sourceFileFor(_nodepath.default.join(projectRoot, fromSrc));
233
- if (source != null) sources[subpath] = source;
234
- }
235
- return sources;
236
- }
237
- [Symbol.dispose]() {
238
- this.stopWatching();
239
- }
240
- getWorkspaceOut() {
241
- const out = _nodepath.default.join(this.#projectConfig.rootDir ?? "./", this.#projectConfig.outDir);
242
- return out;
243
- }
244
- updateSourceFileCache(eventName, file) {
245
- if (!this.#hasLoadedSourceFiles) {
246
- return;
247
- }
248
- switch(eventName){
249
- case _io.WatchEvents.unlink:
250
- this.#sourceFiles.delete(file.relativePath);
251
- return;
252
- case _io.WatchEvents.add:
253
- case _io.WatchEvents.change:
254
- if (this.matchesSourcePattern(file.relativePath)) {
255
- this.#sourceFiles.set(file.relativePath, file);
256
- return;
257
- }
258
- this.#sourceFiles.delete(file.relativePath);
259
- return;
260
- }
261
- }
262
- matchesSourcePattern(relativePath) {
263
- if (_picomatch.default.isMatch(relativePath, this.ignore)) {
264
- return false;
265
- }
266
- return _picomatch.default.isMatch(relativePath, this.include);
267
- }
268
- resolveConfiguration(configurationName) {
269
- const resolvedConfigurationName = configurationName ?? "debug";
270
- const configuration = this.configurations.find((c)=>c.name === resolvedConfigurationName);
271
- if (configuration == null) {
272
- throw new _errors.WorkspaceConfigurationError(`Configuration "${resolvedConfigurationName}" was not found for project "${this.name}"`);
273
- }
274
- return configuration;
275
- }
276
- }
277
- _ts_decorate([
278
- (0, _caching.memoize)(),
279
- _ts_metadata("design:type", Function),
280
- _ts_metadata("design:paramtypes", []),
281
- _ts_metadata("design:returntype", Promise)
282
- ], Project.prototype, "getAllFiles", null);
283
- _ts_decorate([
284
- (0, _caching.cache)(),
285
- _ts_metadata("design:type", Function),
286
- _ts_metadata("design:paramtypes", []),
287
- _ts_metadata("design:returntype", void 0)
288
- ], Project.prototype, "getRootOut", null);
289
- _ts_decorate([
290
- (0, _caching.cache)(),
291
- _ts_metadata("design:type", Function),
292
- _ts_metadata("design:paramtypes", [
293
- void 0
294
- ]),
295
- _ts_metadata("design:returntype", void 0)
296
- ], Project.prototype, "getOutDir", null);
297
- /** The first path an exports value gives, preferring the conditions that name runtime code. */ function firstExportTarget(value) {
298
- if (typeof value === "string") return value;
299
- for (const condition of [
300
- "import",
301
- "default",
302
- "require",
303
- "node",
304
- "types"
305
- ]){
306
- const nested = value[condition];
307
- if (nested != null) return firstExportTarget(nested);
308
- }
309
- return undefined;
310
- }
311
- /** The TypeScript source a built or declaration path came from, if it exists. */ function sourceFileFor(builtPath) {
312
- // A declaration names the file its JavaScript sits next to: `x.d.ts` is `x.js`.
313
- const declaration = builtPath.match(/^(.*)\.d\.([mc]?)ts$/);
314
- const built = declaration == null ? builtPath : `${declaration[1]}.${declaration[2]}js`;
315
- return _sourceextensions.sourceExtensions.candidates(built).find((candidate)=>(0, _nodefs.existsSync)(candidate));
316
- }
@@ -1,81 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", {
3
- value: true
4
- });
5
- Object.defineProperty(exports, "sourceExtensions", {
6
- enumerable: true,
7
- get: function() {
8
- return sourceExtensions;
9
- }
10
- });
11
- const _nodepath = /*#__PURE__*/ _interop_require_default(require("node:path"));
12
- function _interop_require_default(obj) {
13
- return obj && obj.__esModule ? obj : {
14
- default: obj
15
- };
16
- }
17
- /** TypeScript source extensions a workspace compiles. */ const SOURCE = [
18
- ".ts",
19
- ".tsx",
20
- ".mts",
21
- ".cts"
22
- ];
23
- /** The sources an import's extension can name: `./a.js` is `a.ts` or `a.tsx`, `./a.mjs` is `a.mts`. */ const SOURCES_FOR = {
24
- ".js": [
25
- ".ts",
26
- ".tsx"
27
- ],
28
- ".jsx": [
29
- ".tsx"
30
- ],
31
- ".mjs": [
32
- ".mts"
33
- ],
34
- ".cjs": [
35
- ".cts"
36
- ],
37
- "": [
38
- ".ts",
39
- ".tsx"
40
- ]
41
- };
42
- /** Whether a path is a TypeScript source (not a declaration file). */ function isSource(file) {
43
- return SOURCE.some((ext)=>file.endsWith(ext)) && !/\.d\.[mc]?ts$/.test(file);
44
- }
45
- /**
46
- * The source files a path written in an import (or a built path) could name, most likely first:
47
- * itself when it is already a source, else the same stem with each matching source extension.
48
- */ function candidates(file) {
49
- if (isSource(file)) return [
50
- file
51
- ];
52
- const ext = _nodepath.default.extname(file);
53
- const known = SOURCES_FOR[ext];
54
- if (known == null) return [
55
- `${file}.ts`,
56
- `${file}.tsx`
57
- ];
58
- const stem = ext === "" ? file : file.slice(0, -ext.length);
59
- return known.map((sourceExt)=>`${stem}${sourceExt}`);
60
- }
61
- /** The extension a source builds to: `.mts` to `.mjs`, `.cts` to `.cjs`, the rest to `.js`. */ function outputExtension(file) {
62
- if (file.endsWith(".mts")) return ".mjs";
63
- if (file.endsWith(".cts")) return ".cjs";
64
- return ".js";
65
- }
66
- /** The path a source builds to: `a.mts` to `a.mjs`, `a.cts` to `a.cjs`, `a.ts` and `a.tsx` to `a.js`. */ function outputPath(file) {
67
- const ext = _nodepath.default.extname(file);
68
- const stem = ext === "" ? file : file.slice(0, -ext.length);
69
- return `${stem}${outputExtension(file)}`;
70
- }
71
- /** Whether a source is CommonJS (`.cts`); everything else compiles as an ES module. */ function isCommonJs(file) {
72
- return file.endsWith(".cts");
73
- }
74
- const sourceExtensions = {
75
- SOURCE,
76
- isSource,
77
- candidates,
78
- outputExtension,
79
- outputPath,
80
- isCommonJs
81
- };
@@ -1,97 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", {
3
- value: true
4
- });
5
- function _export(target, all) {
6
- for(var name in all)Object.defineProperty(target, name, {
7
- enumerable: true,
8
- get: Object.getOwnPropertyDescriptor(all, name).get
9
- });
10
- }
11
- _export(exports, {
12
- get DEFAULT_COMPILER_OPTIONS () {
13
- return DEFAULT_COMPILER_OPTIONS;
14
- },
15
- get Tsconfig () {
16
- return Tsconfig;
17
- }
18
- });
19
- const _nodefs = /*#__PURE__*/ _interop_require_default(require("node:fs"));
20
- const _nodepath = /*#__PURE__*/ _interop_require_default(require("node:path"));
21
- const _io = require("@decohere/core/io");
22
- const _typescript = /*#__PURE__*/ _interop_require_default(require("typescript"));
23
- const _errors = require("../errors.js");
24
- function _interop_require_default(obj) {
25
- return obj && obj.__esModule ? obj : {
26
- default: obj
27
- };
28
- }
29
- const host = _typescript.default.sys;
30
- host.readFile = (file)=>{
31
- return _nodefs.default.readFileSync(file, {
32
- encoding: "utf8"
33
- });
34
- };
35
- host.readDirectory = (directoryName)=>{
36
- return _nodefs.default.readdirSync(directoryName, {
37
- withFileTypes: true
38
- }).filter((entry)=>entry.isDirectory()).map((entry)=>entry.name);
39
- };
40
- const DEFAULT_COMPILER_OPTIONS = {
41
- emitDeclarationOnly: true,
42
- declaration: true,
43
- baseUrl: "./"
44
- };
45
- class Tsconfig {
46
- static default() {
47
- return new Tsconfig();
48
- }
49
- static async parse(filePath) {
50
- if (!await _io.io.fileExists(filePath)) {
51
- throw new _errors.WorkspaceConfigurationError(`TSConfig not found ${filePath}`);
52
- }
53
- const configFileText = await _io.io.readFile(filePath);
54
- const result = _typescript.default.parseConfigFileTextToJson(filePath, configFileText);
55
- if (result.error) {
56
- const errorMessage = result.error.messageText.toString();
57
- throw new _errors.WorkspaceConfigurationError(`Error parsing ${filePath}. ${errorMessage}`);
58
- }
59
- const dirName = _nodepath.default.resolve(_nodepath.default.dirname(filePath));
60
- const configParseResult = _typescript.default.parseJsonConfigFileContent(result.config, host, dirName);
61
- return new Tsconfig({
62
- compilerOptions: configParseResult.options,
63
- errors: configParseResult.errors
64
- });
65
- }
66
- static parseSync(filePath) {
67
- if (!Tsconfig.fileExistsSync(filePath)) {
68
- throw new _errors.WorkspaceConfigurationError(`TSConfig not found ${filePath}`);
69
- }
70
- const configFileText = _nodefs.default.readFileSync(filePath, "utf8");
71
- const result = _typescript.default.parseConfigFileTextToJson(filePath, configFileText);
72
- if (result.error) {
73
- const errorMessage = result.error.messageText.toString();
74
- throw new _errors.WorkspaceConfigurationError(`Error parsing ${filePath}. ${errorMessage}`);
75
- }
76
- const dirName = _nodepath.default.resolve(_nodepath.default.dirname(filePath));
77
- const configParseResult = _typescript.default.parseJsonConfigFileContent(result.config, host, dirName);
78
- return new Tsconfig({
79
- compilerOptions: configParseResult.options,
80
- errors: configParseResult.errors
81
- });
82
- }
83
- static fileExistsSync(filePath) {
84
- try {
85
- return _nodefs.default.statSync(filePath).isFile();
86
- } catch {
87
- return false;
88
- }
89
- }
90
- constructor(data = {
91
- compilerOptions: DEFAULT_COMPILER_OPTIONS
92
- }){
93
- Object.assign(this, data);
94
- }
95
- compilerOptions;
96
- errors;
97
- }
@@ -1,7 +0,0 @@
1
- /**
2
- * Generic configuration for a workspace build profile.
3
- * Concrete tools (e.g. @decohere/forge) extend this with tool-specific fields.
4
- */ "use strict";
5
- Object.defineProperty(exports, "__esModule", {
6
- value: true
7
- });
@@ -1,153 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", {
3
- value: true
4
- });
5
- Object.defineProperty(exports, "Workspace", {
6
- enumerable: true,
7
- get: function() {
8
- return Workspace;
9
- }
10
- });
11
- const _decorators = require("@decohere/crucible/decorators");
12
- const _collections = require("@decohere/core/collections");
13
- const _extensibility = require("@decohere/core/extensibility");
14
- const _rxjs = require("rxjs");
15
- const _errors = require("../errors.js");
16
- const _haspackagejsonmixin = require("./has-package-json.mixin.js");
17
- const _hastsconfigmixin = require("./has-tsconfig.mixin.js");
18
- const _packagealiases = require("./package-aliases.js");
19
- const _packagejsonmodel = require("./package-json.model.js");
20
- const _projectmodel = require("./project.model.js");
21
- function _ts_decorate(decorators, target, key, desc) {
22
- var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
23
- if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
24
- else for(var i = decorators.length - 1; i >= 0; i--)if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
25
- return c > 3 && r && Object.defineProperty(target, key, r), r;
26
- }
27
- function _ts_metadata(k, v) {
28
- if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
29
- }
30
- class Workspace extends (0, _extensibility.mixwith)(_haspackagejsonmixin.HasPackageJson, _hastsconfigmixin.HasTsConfig) {
31
- packageJson;
32
- #name;
33
- #config;
34
- #projectSeeds = [];
35
- #projectCache = new Map();
36
- /**
37
- * Each project's source file paths as a set, so `findProject` is a lookup rather than a scan
38
- * of every file: the Vitest plugin asks once per transformed file. Keyed by the list
39
- * `getAllFiles` returns, so a new list (after its cache is flushed) gets a new set.
40
- */ #sourcePaths = new WeakMap();
41
- #projectFileChangedSubject = new _rxjs.Subject();
42
- #projectWatchSubscriptions = new Map();
43
- #watchedProjects = [];
44
- constructor(options = {}){
45
- super();
46
- const { packageJson, config, projects } = options;
47
- this.#name = packageJson?.name ?? "WORKSPACE";
48
- this.packageJson = packageJson ?? new _packagejsonmodel.PackageJson();
49
- this.#config = config ?? {};
50
- this.#projectSeeds = projects ?? [];
51
- this.validateWorkspace();
52
- }
53
- get name() {
54
- return this.#name;
55
- }
56
- get projectSeeds() {
57
- return this.#projectSeeds;
58
- }
59
- getProjects(configuration) {
60
- const cached = this.#projectCache.get(configuration);
61
- if (cached != null) {
62
- return cached;
63
- }
64
- const projects = this.#projectSeeds.map((seed)=>new _projectmodel.Project(seed.name, seed.config ?? {}, configuration));
65
- this.#projectCache.set(configuration, projects);
66
- return projects;
67
- }
68
- get rootDir() {
69
- return this.#config.rootDir ?? "./";
70
- }
71
- get packageJsonDirectory() {
72
- return this.rootDir;
73
- }
74
- get tsConfigDirectory() {
75
- return this.rootDir;
76
- }
77
- get fallbackTsConfigDirectory() {
78
- return undefined;
79
- }
80
- /**
81
- * Package-name aliases for this configuration: workspace convention, then
82
- * workspace `tsconfig.json` `paths` overrides. Forge and Flux must use this
83
- * instead of assembling the map themselves.
84
- */ getPackageAliases(configuration) {
85
- const tsconfig = this.findTsConfigPath() != null ? this.getTsConfigSync() : undefined;
86
- const baseUrl = typeof tsconfig?.compilerOptions?.baseUrl === "string" && tsconfig.compilerOptions.baseUrl.length > 0 ? tsconfig.compilerOptions.baseUrl : this.rootDir;
87
- return _packagealiases.packageAliases.build(this.getProjects(configuration), {
88
- baseUrl,
89
- tsconfigPaths: tsconfig?.compilerOptions?.paths
90
- });
91
- }
92
- async watch(configuration) {
93
- this.stopWatching();
94
- const projects = this.getProjects(configuration);
95
- this.#watchedProjects = projects;
96
- for (const project of projects){
97
- await project.watch(configuration);
98
- const subscription = project.projectFileChanged$.subscribe((evt)=>this.#projectFileChangedSubject.next(evt));
99
- this.#projectWatchSubscriptions.set(project.projectDirectory, subscription);
100
- }
101
- }
102
- stopWatching() {
103
- for (const subscription of this.#projectWatchSubscriptions.values()){
104
- subscription.unsubscribe();
105
- }
106
- for (const project of this.#watchedProjects){
107
- project.stopWatching();
108
- }
109
- this.#watchedProjects = [];
110
- this.#projectWatchSubscriptions.clear();
111
- }
112
- [Symbol.dispose]() {
113
- this.stopWatching();
114
- }
115
- get projectFileChanged$() {
116
- return this.#projectFileChangedSubject.asObservable();
117
- }
118
- async findProject(filePath, buildConfig) {
119
- for (const project of this.getProjects(buildConfig)){
120
- if ((await this.sourcePathsOf(project)).has(filePath)) {
121
- return project;
122
- }
123
- }
124
- return undefined;
125
- }
126
- async sourcePathsOf(project) {
127
- const files = await project.getAllFiles();
128
- const cached = this.#sourcePaths.get(files);
129
- if (cached != null) return cached;
130
- const paths = new Set(files.map((file)=>file.fullPath));
131
- this.#sourcePaths.set(files, paths);
132
- return paths;
133
- }
134
- validateWorkspace() {
135
- const errors = this.findDuplicateProjectSeeds(this.#projectSeeds);
136
- if (errors.length > 0) {
137
- throw new _errors.WorkspaceConfigurationError(errors.join("\n"));
138
- }
139
- }
140
- findDuplicateProjectSeeds(seeds) {
141
- const duplicates = _collections.collections.findDuplicatesByKey([
142
- ...seeds
143
- ], "name");
144
- return duplicates.map(([name, group])=>`Duplicate project name "${name}" found at: ${group.map((seed)=>seed.config?.projectDir ?? name).join(", ")}`);
145
- }
146
- }
147
- Workspace = _ts_decorate([
148
- (0, _decorators.injectable)(),
149
- _ts_metadata("design:type", Function),
150
- _ts_metadata("design:paramtypes", [
151
- typeof Partial === "undefined" ? Object : Partial
152
- ])
153
- ], Workspace);
package/es6/src/const.js DELETED
@@ -1,36 +0,0 @@
1
- export const TS_CONFIG = "tsconfig.json";
2
- export const PACKAGE_JSON = "package.json";
3
- export const NODE_MODULES = "node_modules";
4
- export const FIXTURES = "__fixtures__";
5
- export const WORKSPACE_CONFIG = ".decohere.js";
6
- export const PROJECTS_DIR = "projects";
7
- export const WorkspaceDefaults = {
8
- rootDir: "./",
9
- outDir: "dist",
10
- includeProjects: [
11
- `${PROJECTS_DIR}/**/${PACKAGE_JSON}`
12
- ],
13
- ignoreProjects: [
14
- `**/${NODE_MODULES}/**`,
15
- `**/${FIXTURES}/**`,
16
- "**/dist/**"
17
- ],
18
- include: [
19
- "**/*.ts",
20
- "**/*.tsx",
21
- "**/*.mts",
22
- "**/*.cts"
23
- ],
24
- ignore: [
25
- "**/*.d.ts",
26
- "**/*.d.mts",
27
- "**/*.d.cts",
28
- `**/${NODE_MODULES}/**`
29
- ],
30
- copyFiles: [],
31
- configurations: [
32
- {
33
- name: "debug"
34
- }
35
- ]
36
- };
package/es6/src/errors.js DELETED
@@ -1,2 +0,0 @@
1
- export class WorkspaceConfigurationError extends Error {
2
- }