@abreen/tada 1.13.7 → 1.13.9
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/build/generate-content-assets.ts +37 -175
- package/build/pipeline.ts +1 -1
- package/build/source-model.ts +2 -14
- package/build/types.d.ts +0 -12
- package/build/watch/build-full.ts +26 -52
- package/build/watch/build-helpers.ts +66 -0
- package/build/watch/build-incremental.ts +32 -60
- package/build/watch/build-result.ts +19 -0
- package/build/watch/compiler.ts +25 -61
- package/build/watch/config-paths.ts +56 -0
- package/build/watch/engine.ts +199 -0
- package/{watch → build/watch}/fs-commit.ts +1 -3
- package/build/watch/index.ts +1 -1
- package/build/watch/mutations.ts +23 -25
- package/build/watch/planner.ts +14 -78
- package/build/watch/runtime.ts +26 -38
- package/build/watch/snapshot.ts +26 -47
- package/build/watch/types.d.ts +84 -0
- package/build/watch/validation.ts +1 -1
- package/package.json +1 -2
- package/build/watch-reachability-state.ts +0 -305
- package/watch/engine.ts +0 -296
- package/watch/events.ts +0 -10
- package/watch/types.d.ts +0 -103
package/build/watch/planner.ts
CHANGED
|
@@ -1,16 +1,12 @@
|
|
|
1
1
|
import path from 'path';
|
|
2
|
-
import {
|
|
3
|
-
getProjectConfigBaseName,
|
|
4
|
-
getSiteConfigBaseName,
|
|
5
|
-
getSupportedConfigFilePaths,
|
|
6
|
-
} from '../config-files';
|
|
7
2
|
import { loadProjectConfig } from '../config-loader';
|
|
8
3
|
import { getProjectConfigDir } from '../templates';
|
|
9
|
-
import type { ChangeBatch } from '
|
|
4
|
+
import type { ChangeBatch } from './types';
|
|
10
5
|
import type { TadaProjectScan, TadaSnapshot } from './snapshot';
|
|
6
|
+
import { classifyWatchConfigPath } from './config-paths';
|
|
11
7
|
|
|
12
|
-
export interface
|
|
13
|
-
kind: '
|
|
8
|
+
export interface TadaIncrementalWatchPlan {
|
|
9
|
+
kind: 'incremental';
|
|
14
10
|
scan: TadaProjectScan;
|
|
15
11
|
contentToRender: Set<string>;
|
|
16
12
|
publicToRender: Set<string>;
|
|
@@ -18,6 +14,8 @@ export interface TadaWatchPlan {
|
|
|
18
14
|
publicToRemove: Set<string>;
|
|
19
15
|
}
|
|
20
16
|
|
|
17
|
+
export type TadaWatchPlan = { kind: 'full' } | TadaIncrementalWatchPlan;
|
|
18
|
+
|
|
21
19
|
export function diffAuthorKeys(previous: unknown, next: unknown): Set<string> {
|
|
22
20
|
const previousMap =
|
|
23
21
|
previous && typeof previous === 'object'
|
|
@@ -60,7 +58,7 @@ export function createTadaWatchPlan({
|
|
|
60
58
|
batch,
|
|
61
59
|
scan,
|
|
62
60
|
}: {
|
|
63
|
-
snapshot: TadaSnapshot
|
|
61
|
+
snapshot: TadaSnapshot;
|
|
64
62
|
batch: ChangeBatch;
|
|
65
63
|
scan: TadaProjectScan;
|
|
66
64
|
}): TadaWatchPlan {
|
|
@@ -69,66 +67,24 @@ export function createTadaWatchPlan({
|
|
|
69
67
|
const contentToRemove = new Set<string>();
|
|
70
68
|
const publicToRemove = new Set<string>();
|
|
71
69
|
const projectConfigDir = getProjectConfigDir();
|
|
72
|
-
const siteConfigPaths = new Set(
|
|
73
|
-
getSupportedConfigFilePaths('.', getSiteConfigBaseName('dev')).map(
|
|
74
|
-
filePath => path.resolve(filePath),
|
|
75
|
-
),
|
|
76
|
-
);
|
|
77
|
-
const navPaths = new Set(
|
|
78
|
-
getSupportedConfigFilePaths(
|
|
79
|
-
projectConfigDir,
|
|
80
|
-
getProjectConfigBaseName('nav'),
|
|
81
|
-
).map(filePath => path.resolve(filePath)),
|
|
82
|
-
);
|
|
83
|
-
const authorsPaths = new Set(
|
|
84
|
-
getSupportedConfigFilePaths(
|
|
85
|
-
projectConfigDir,
|
|
86
|
-
getProjectConfigBaseName('authors'),
|
|
87
|
-
).map(filePath => path.resolve(filePath)),
|
|
88
|
-
);
|
|
89
|
-
|
|
90
|
-
if (!snapshot) {
|
|
91
|
-
return {
|
|
92
|
-
kind: 'full',
|
|
93
|
-
scan,
|
|
94
|
-
contentToRender,
|
|
95
|
-
publicToRender,
|
|
96
|
-
contentToRemove,
|
|
97
|
-
publicToRemove,
|
|
98
|
-
};
|
|
99
|
-
}
|
|
100
70
|
|
|
101
71
|
for (const change of batch.changes) {
|
|
102
|
-
const
|
|
103
|
-
if (
|
|
104
|
-
return {
|
|
105
|
-
kind: 'full',
|
|
106
|
-
scan,
|
|
107
|
-
contentToRender,
|
|
108
|
-
publicToRender,
|
|
109
|
-
contentToRemove,
|
|
110
|
-
publicToRemove,
|
|
111
|
-
};
|
|
72
|
+
const configKind = classifyWatchConfigPath(change.path);
|
|
73
|
+
if (configKind === 'site' || configKind === 'nav') {
|
|
74
|
+
return { kind: 'full' };
|
|
112
75
|
}
|
|
113
76
|
}
|
|
114
77
|
|
|
115
78
|
for (const change of batch.changes) {
|
|
116
79
|
const resolvedPath = path.resolve(change.path);
|
|
117
|
-
if (
|
|
80
|
+
if (classifyWatchConfigPath(resolvedPath) === 'authors') {
|
|
118
81
|
const nextAuthorsData = loadProjectConfig(
|
|
119
82
|
projectConfigDir,
|
|
120
83
|
'authors',
|
|
121
84
|
snapshot.siteVariables,
|
|
122
85
|
)?.value;
|
|
123
86
|
if (snapshot.authorsData === undefined || nextAuthorsData === undefined) {
|
|
124
|
-
return {
|
|
125
|
-
kind: 'full',
|
|
126
|
-
scan,
|
|
127
|
-
contentToRender,
|
|
128
|
-
publicToRender,
|
|
129
|
-
contentToRemove,
|
|
130
|
-
publicToRemove,
|
|
131
|
-
};
|
|
87
|
+
return { kind: 'full' };
|
|
132
88
|
}
|
|
133
89
|
const changedAuthorKeys = diffAuthorKeys(
|
|
134
90
|
snapshot.authorsData,
|
|
@@ -144,17 +100,6 @@ export function createTadaWatchPlan({
|
|
|
144
100
|
contentToRender.add(resolvedPath);
|
|
145
101
|
} else if (snapshot.contentRecords.has(resolvedPath)) {
|
|
146
102
|
contentToRemove.add(resolvedPath);
|
|
147
|
-
const previousRecord = snapshot.contentRecords.get(resolvedPath)!;
|
|
148
|
-
for (const partialPath of previousRecord.partialDeps) {
|
|
149
|
-
addDependents(
|
|
150
|
-
contentToRender,
|
|
151
|
-
snapshot.reversePartialDeps,
|
|
152
|
-
partialPath,
|
|
153
|
-
);
|
|
154
|
-
}
|
|
155
|
-
for (const tracePath of previousRecord.traceDeps) {
|
|
156
|
-
addDependents(contentToRender, snapshot.reverseTraceDeps, tracePath);
|
|
157
|
-
}
|
|
158
103
|
}
|
|
159
104
|
|
|
160
105
|
if (scan.publicFiles.has(resolvedPath)) {
|
|
@@ -168,15 +113,13 @@ export function createTadaWatchPlan({
|
|
|
168
113
|
}
|
|
169
114
|
|
|
170
115
|
const changedTargets = new Set<string>();
|
|
171
|
-
const
|
|
172
|
-
for (const target of snapshot.validTargets) {
|
|
116
|
+
for (const target of snapshot.scan.validTargets) {
|
|
173
117
|
if (!scan.validTargets.has(target)) {
|
|
174
118
|
changedTargets.add(target);
|
|
175
|
-
removedTargets.add(target);
|
|
176
119
|
}
|
|
177
120
|
}
|
|
178
121
|
for (const target of scan.validTargets) {
|
|
179
|
-
if (!snapshot.validTargets.has(target)) {
|
|
122
|
+
if (!snapshot.scan.validTargets.has(target)) {
|
|
180
123
|
changedTargets.add(target);
|
|
181
124
|
}
|
|
182
125
|
}
|
|
@@ -184,13 +127,6 @@ export function createTadaWatchPlan({
|
|
|
184
127
|
addDependents(contentToRender, snapshot.reverseInternalTargetDeps, target);
|
|
185
128
|
}
|
|
186
129
|
|
|
187
|
-
if (removedTargets.size > 0 && contentToRender.size === 0) {
|
|
188
|
-
const rootOwner = snapshot.outputOwners.get('index.html');
|
|
189
|
-
if (rootOwner?.kind === 'content') {
|
|
190
|
-
contentToRender.add(rootOwner.sourcePath);
|
|
191
|
-
}
|
|
192
|
-
}
|
|
193
|
-
|
|
194
130
|
for (const [outputPath, owner] of snapshot.outputOwners) {
|
|
195
131
|
const nextContentOwner = scan.contentOwners.get(outputPath);
|
|
196
132
|
const nextPublicOwner = scan.publicOwners.get(outputPath);
|
package/build/watch/runtime.ts
CHANGED
|
@@ -3,9 +3,7 @@ import { B } from '../colors';
|
|
|
3
3
|
import { makeLogger, printFlair } from '../log';
|
|
4
4
|
import { startServer } from '../serve';
|
|
5
5
|
import { WatchPagefindRunner } from '../pagefind';
|
|
6
|
-
import type {
|
|
7
|
-
import type { TadaSnapshot } from './snapshot';
|
|
8
|
-
import type { WatchLifecycleEvent } from '../../watch/types';
|
|
6
|
+
import type { WatchLifecycleEvent } from './types';
|
|
9
7
|
import {
|
|
10
8
|
WATCH_RELOAD_MESSAGE_REBUILDING,
|
|
11
9
|
WATCH_RELOAD_MESSAGE_RELOAD,
|
|
@@ -30,7 +28,6 @@ export class TadaWatchRuntime {
|
|
|
30
28
|
private httpPort: number | undefined;
|
|
31
29
|
private distDir: string;
|
|
32
30
|
private server: Bun.Server<undefined> | null;
|
|
33
|
-
private lastBuildFailed: boolean;
|
|
34
31
|
private pagefindRunner: WatchPagefindRunner | undefined;
|
|
35
32
|
private pagefindSiteVariablesKey: string | undefined;
|
|
36
33
|
|
|
@@ -38,7 +35,6 @@ export class TadaWatchRuntime {
|
|
|
38
35
|
this.httpPort = httpPort;
|
|
39
36
|
this.distDir = distDir;
|
|
40
37
|
this.server = null;
|
|
41
|
-
this.lastBuildFailed = false;
|
|
42
38
|
this.pagefindSiteVariablesKey = undefined;
|
|
43
39
|
}
|
|
44
40
|
|
|
@@ -68,51 +64,45 @@ export class TadaWatchRuntime {
|
|
|
68
64
|
wslog.debug`WebSocket server listening at ws://localhost:${this.server.port}${WATCH_RELOAD_PATH}`;
|
|
69
65
|
}
|
|
70
66
|
|
|
71
|
-
async onEvent(
|
|
72
|
-
event: WatchLifecycleEvent<TadaSnapshot, TadaBuildMeta>,
|
|
73
|
-
): Promise<void> {
|
|
67
|
+
async onEvent(event: WatchLifecycleEvent): Promise<void> {
|
|
74
68
|
switch (event.kind) {
|
|
75
69
|
case 'build-started':
|
|
76
|
-
if (!event.
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
70
|
+
if (!event.batch) {
|
|
71
|
+
return;
|
|
72
|
+
}
|
|
73
|
+
for (const change of event.batch.changes) {
|
|
74
|
+
log.event`${B`${path.basename(change.path)}`} ${describeChange(change.kind)}`;
|
|
81
75
|
}
|
|
76
|
+
this.broadcast(WATCH_RELOAD_MESSAGE_REBUILDING);
|
|
82
77
|
return;
|
|
83
78
|
case 'build-succeeded': {
|
|
84
|
-
const recoveredFromFailure = this.lastBuildFailed;
|
|
85
|
-
this.lastBuildFailed = false;
|
|
86
79
|
printFlair();
|
|
87
80
|
this.ensureServerStarted();
|
|
88
|
-
if (
|
|
81
|
+
if (event.batch) {
|
|
89
82
|
this.broadcast(WATCH_RELOAD_MESSAGE_RELOAD);
|
|
90
83
|
}
|
|
91
|
-
if (event.meta
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
)
|
|
98
|
-
|
|
99
|
-
this.pagefindSiteVariablesKey = siteVariablesKey;
|
|
100
|
-
}
|
|
101
|
-
this.pagefindRunner.update(
|
|
102
|
-
this.distDir,
|
|
103
|
-
event.meta.htmlAssetsByPath,
|
|
104
|
-
event.meta.htmlAnalysisByPath,
|
|
105
|
-
);
|
|
106
|
-
setImmediate(() => this.pagefindRunner!.run());
|
|
107
|
-
} else {
|
|
108
|
-
this.pagefindRunner = undefined;
|
|
109
|
-
this.pagefindSiteVariablesKey = undefined;
|
|
84
|
+
if (event.meta.siteVariables.features.search !== false) {
|
|
85
|
+
const siteVariablesKey = JSON.stringify(event.meta.siteVariables);
|
|
86
|
+
if (
|
|
87
|
+
!this.pagefindRunner ||
|
|
88
|
+
this.pagefindSiteVariablesKey !== siteVariablesKey
|
|
89
|
+
) {
|
|
90
|
+
this.pagefindRunner = new WatchPagefindRunner();
|
|
91
|
+
this.pagefindSiteVariablesKey = siteVariablesKey;
|
|
110
92
|
}
|
|
93
|
+
this.pagefindRunner.update(
|
|
94
|
+
this.distDir,
|
|
95
|
+
event.meta.htmlAssetsByPath,
|
|
96
|
+
event.meta.htmlAnalysisByPath,
|
|
97
|
+
);
|
|
98
|
+
setImmediate(() => this.pagefindRunner!.run());
|
|
99
|
+
} else {
|
|
100
|
+
this.pagefindRunner = undefined;
|
|
101
|
+
this.pagefindSiteVariablesKey = undefined;
|
|
111
102
|
}
|
|
112
103
|
return;
|
|
113
104
|
}
|
|
114
105
|
case 'build-failed':
|
|
115
|
-
this.lastBuildFailed = true;
|
|
116
106
|
for (const diagnostic of event.diagnostics) {
|
|
117
107
|
log.error`${diagnostic.message}`;
|
|
118
108
|
}
|
|
@@ -120,8 +110,6 @@ export class TadaWatchRuntime {
|
|
|
120
110
|
case 'watching':
|
|
121
111
|
log.info`Watching for changes...`;
|
|
122
112
|
return;
|
|
123
|
-
case 'build-skipped':
|
|
124
|
-
return;
|
|
125
113
|
}
|
|
126
114
|
}
|
|
127
115
|
}
|
package/build/watch/snapshot.ts
CHANGED
|
@@ -8,6 +8,7 @@ import {
|
|
|
8
8
|
updateProjectScan,
|
|
9
9
|
} from '../source-model';
|
|
10
10
|
import type { Asset, HtmlOutputAnalysis, SiteVariables } from '../types';
|
|
11
|
+
import type { TadaBuildMeta } from './compiler-types';
|
|
11
12
|
|
|
12
13
|
export interface TadaSourceRecord {
|
|
13
14
|
sourcePath: string;
|
|
@@ -21,28 +22,24 @@ export interface TadaSourceRecord {
|
|
|
21
22
|
authorKey?: string;
|
|
22
23
|
}
|
|
23
24
|
|
|
25
|
+
export interface TadaOutputOwner {
|
|
26
|
+
kind: 'content' | 'public';
|
|
27
|
+
sourcePath: string;
|
|
28
|
+
}
|
|
29
|
+
|
|
24
30
|
export interface TadaSnapshot {
|
|
25
31
|
siteVariables: SiteVariables;
|
|
26
32
|
assetFiles: string[];
|
|
27
33
|
navData: unknown;
|
|
28
34
|
authorsData: unknown;
|
|
29
|
-
processedExts: Set<string>;
|
|
30
35
|
contentRecords: Map<string, TadaSourceRecord>;
|
|
31
36
|
publicRecords: Map<string, TadaSourceRecord>;
|
|
32
|
-
outputOwners: Map<string,
|
|
37
|
+
outputOwners: Map<string, TadaOutputOwner>;
|
|
33
38
|
reversePartialDeps: Map<string, Set<string>>;
|
|
34
39
|
reverseTraceDeps: Map<string, Set<string>>;
|
|
35
40
|
reverseInternalTargetDeps: Map<string, Set<string>>;
|
|
36
41
|
reverseAuthorDeps: Map<string, Set<string>>;
|
|
37
|
-
|
|
38
|
-
buildContentFiles: Set<string>;
|
|
39
|
-
publicFiles: Set<string>;
|
|
40
|
-
literateJavaOutputPaths: Set<string>;
|
|
41
|
-
contentOwners: Map<string, string>;
|
|
42
|
-
publicOwners: Map<string, string>;
|
|
43
|
-
sourceOutputPaths: Map<string, Set<string>>;
|
|
44
|
-
sourceTargetPaths: Map<string, Set<string>>;
|
|
45
|
-
validTargets: Set<string>;
|
|
42
|
+
scan: TadaProjectScan;
|
|
46
43
|
}
|
|
47
44
|
|
|
48
45
|
function buildReverseMap(
|
|
@@ -63,22 +60,11 @@ function buildReverseMap(
|
|
|
63
60
|
return reverse;
|
|
64
61
|
}
|
|
65
62
|
|
|
66
|
-
function cloneSetMap(
|
|
67
|
-
source: Map<string, Set<string>>,
|
|
68
|
-
): Map<string, Set<string>> {
|
|
69
|
-
return new Map(
|
|
70
|
-
[...source.entries()].map(([key, values]) => [key, new Set(values)]),
|
|
71
|
-
);
|
|
72
|
-
}
|
|
73
|
-
|
|
74
63
|
export function collectOutputOwners(snapshot: {
|
|
75
64
|
contentRecords: Map<string, TadaSourceRecord>;
|
|
76
65
|
publicRecords: Map<string, TadaSourceRecord>;
|
|
77
|
-
}): Map<string,
|
|
78
|
-
const owners = new Map<
|
|
79
|
-
string,
|
|
80
|
-
{ kind: 'content' | 'public'; sourcePath: string }
|
|
81
|
-
>();
|
|
66
|
+
}): Map<string, TadaOutputOwner> {
|
|
67
|
+
const owners = new Map<string, TadaOutputOwner>();
|
|
82
68
|
|
|
83
69
|
for (const record of snapshot.contentRecords.values()) {
|
|
84
70
|
for (const outputPath of record.outputs.keys()) {
|
|
@@ -116,23 +102,12 @@ export function createSnapshot({
|
|
|
116
102
|
publicRecords: Map<string, TadaSourceRecord>;
|
|
117
103
|
}): TadaSnapshot {
|
|
118
104
|
const allRecords = [...contentRecords.values()];
|
|
119
|
-
const reverseAuthorDeps = new Map<string, Set<string>>();
|
|
120
|
-
for (const record of allRecords) {
|
|
121
|
-
if (!record.authorKey) {
|
|
122
|
-
continue;
|
|
123
|
-
}
|
|
124
|
-
if (!reverseAuthorDeps.has(record.authorKey)) {
|
|
125
|
-
reverseAuthorDeps.set(record.authorKey, new Set());
|
|
126
|
-
}
|
|
127
|
-
reverseAuthorDeps.get(record.authorKey)!.add(record.sourcePath);
|
|
128
|
-
}
|
|
129
105
|
|
|
130
106
|
return {
|
|
131
107
|
siteVariables,
|
|
132
108
|
assetFiles,
|
|
133
109
|
navData,
|
|
134
110
|
authorsData,
|
|
135
|
-
processedExts: scan.processedExts,
|
|
136
111
|
contentRecords,
|
|
137
112
|
publicRecords,
|
|
138
113
|
outputOwners: collectOutputOwners({ contentRecords, publicRecords }),
|
|
@@ -145,16 +120,10 @@ export function createSnapshot({
|
|
|
145
120
|
allRecords,
|
|
146
121
|
record => record.internalTargets,
|
|
147
122
|
),
|
|
148
|
-
reverseAuthorDeps,
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
literateJavaOutputPaths: new Set(scan.literateJavaOutputPaths),
|
|
153
|
-
contentOwners: new Map(scan.contentOwners),
|
|
154
|
-
publicOwners: new Map(scan.publicOwners),
|
|
155
|
-
sourceOutputPaths: cloneSetMap(scan.sourceOutputPaths),
|
|
156
|
-
sourceTargetPaths: cloneSetMap(scan.sourceTargetPaths),
|
|
157
|
-
validTargets: new Set(scan.validTargets),
|
|
123
|
+
reverseAuthorDeps: buildReverseMap(allRecords, record =>
|
|
124
|
+
record.authorKey ? [record.authorKey] : [],
|
|
125
|
+
),
|
|
126
|
+
scan,
|
|
158
127
|
};
|
|
159
128
|
}
|
|
160
129
|
|
|
@@ -214,14 +183,24 @@ export function collectHtmlAnalysisByPath(
|
|
|
214
183
|
): Map<string, HtmlOutputAnalysis> {
|
|
215
184
|
const htmlAnalysisByPath = new Map<string, HtmlOutputAnalysis>();
|
|
216
185
|
for (const record of contentRecords.values()) {
|
|
217
|
-
|
|
218
|
-
|
|
186
|
+
if (!record.htmlAnalysisByOutputPath) {
|
|
187
|
+
continue;
|
|
188
|
+
}
|
|
189
|
+
for (const [outputPath, analysis] of record.htmlAnalysisByOutputPath) {
|
|
219
190
|
htmlAnalysisByPath.set(outputPath, cloneHtmlOutputAnalysis(analysis));
|
|
220
191
|
}
|
|
221
192
|
}
|
|
222
193
|
return htmlAnalysisByPath;
|
|
223
194
|
}
|
|
224
195
|
|
|
196
|
+
export function createBuildMeta(snapshot: TadaSnapshot): TadaBuildMeta {
|
|
197
|
+
return {
|
|
198
|
+
htmlAssetsByPath: collectHtmlAssetsByPath(snapshot.contentRecords),
|
|
199
|
+
htmlAnalysisByPath: collectHtmlAnalysisByPath(snapshot.contentRecords),
|
|
200
|
+
siteVariables: snapshot.siteVariables,
|
|
201
|
+
};
|
|
202
|
+
}
|
|
203
|
+
|
|
225
204
|
export function normalizeInternalTarget(target: string): string {
|
|
226
205
|
return normalizeOutputPath(target);
|
|
227
206
|
}
|
|
@@ -0,0 +1,84 @@
|
|
|
1
|
+
import type { ChokidarOptions } from 'chokidar';
|
|
2
|
+
import type { TadaBuildMeta } from './compiler-types';
|
|
3
|
+
import type { TadaSnapshot } from './snapshot';
|
|
4
|
+
|
|
5
|
+
export type WatchEventKind = 'add' | 'change' | 'unlink';
|
|
6
|
+
|
|
7
|
+
export interface FileChange {
|
|
8
|
+
path: string;
|
|
9
|
+
kind: WatchEventKind;
|
|
10
|
+
}
|
|
11
|
+
|
|
12
|
+
export interface ChangeBatch {
|
|
13
|
+
changes: FileChange[];
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
export interface WatchTarget {
|
|
17
|
+
path: string;
|
|
18
|
+
chokidar?: ChokidarOptions;
|
|
19
|
+
filter?: (filePath: string) => boolean;
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
export interface WatchDiagnostic {
|
|
23
|
+
message: string;
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
export interface WriteFileMutation {
|
|
27
|
+
kind: 'write';
|
|
28
|
+
path: string;
|
|
29
|
+
content: string | Buffer;
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
export interface DeleteFileMutation {
|
|
33
|
+
kind: 'delete';
|
|
34
|
+
path: string;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
export type FileMutation = WriteFileMutation | DeleteFileMutation;
|
|
38
|
+
|
|
39
|
+
export interface ReplaceRootCommitPlan {
|
|
40
|
+
kind: 'replace-root';
|
|
41
|
+
stagedPath: string;
|
|
42
|
+
targetPath: string;
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
export interface ApplyMutationsCommitPlan {
|
|
46
|
+
kind: 'apply-mutations';
|
|
47
|
+
rootDir: string;
|
|
48
|
+
mutations: FileMutation[];
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
export type CommitPlan = ReplaceRootCommitPlan | ApplyMutationsCommitPlan;
|
|
52
|
+
|
|
53
|
+
export type CompilerBuildResult =
|
|
54
|
+
| {
|
|
55
|
+
ok: true;
|
|
56
|
+
snapshot: TadaSnapshot;
|
|
57
|
+
commit: CommitPlan;
|
|
58
|
+
meta: TadaBuildMeta;
|
|
59
|
+
}
|
|
60
|
+
| { ok: false; diagnostics: WatchDiagnostic[] };
|
|
61
|
+
|
|
62
|
+
export interface WatchCompiler {
|
|
63
|
+
getWatchTargets(): WatchTarget[];
|
|
64
|
+
build(
|
|
65
|
+
snapshot: TadaSnapshot | undefined,
|
|
66
|
+
batch?: ChangeBatch,
|
|
67
|
+
): Promise<CompilerBuildResult>;
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
export type WatchLifecycleEvent =
|
|
71
|
+
| { kind: 'watching' }
|
|
72
|
+
| { kind: 'build-started'; batch?: ChangeBatch }
|
|
73
|
+
| { kind: 'build-succeeded'; batch?: ChangeBatch; meta: TadaBuildMeta }
|
|
74
|
+
| {
|
|
75
|
+
kind: 'build-failed';
|
|
76
|
+
batch?: ChangeBatch;
|
|
77
|
+
diagnostics: WatchDiagnostic[];
|
|
78
|
+
};
|
|
79
|
+
|
|
80
|
+
export interface WatchEngineOptions {
|
|
81
|
+
compiler: WatchCompiler;
|
|
82
|
+
debounceMs?: number;
|
|
83
|
+
onEvent?: (event: WatchLifecycleEvent) => void | Promise<void>;
|
|
84
|
+
}
|
|
@@ -2,7 +2,7 @@ import { B } from '../colors';
|
|
|
2
2
|
import { makeLogger } from '../log';
|
|
3
3
|
import { config, getConfigFileName } from '../templates';
|
|
4
4
|
import { validateConfigLinks } from '../validate-config-links';
|
|
5
|
-
import type { WatchDiagnostic } from '
|
|
5
|
+
import type { WatchDiagnostic } from './types';
|
|
6
6
|
import { assertNoOutputPathConflicts, type TadaProjectScan } from './snapshot';
|
|
7
7
|
|
|
8
8
|
const log = makeLogger(import.meta.url);
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@abreen/tada",
|
|
3
|
-
"version": "1.13.
|
|
3
|
+
"version": "1.13.9",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"description": "A static site generator",
|
|
6
6
|
"license": "MIT",
|
|
@@ -15,7 +15,6 @@
|
|
|
15
15
|
"files": [
|
|
16
16
|
"bin/",
|
|
17
17
|
"build/",
|
|
18
|
-
"watch/",
|
|
19
18
|
"src/",
|
|
20
19
|
"templates/",
|
|
21
20
|
"fonts/",
|