prosebook 0.0.1 → 0.2.0
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/LICENSE +21 -0
- package/README.md +604 -0
- package/dist/cli.d.ts +1 -0
- package/dist/cli.js +508 -0
- package/dist/cli.js.map +1 -0
- package/dist/config-D--RITk2.js +1208 -0
- package/dist/config-D--RITk2.js.map +1 -0
- package/dist/config-_4HfnJQu.d.ts +517 -0
- package/dist/config-_4HfnJQu.d.ts.map +1 -0
- package/dist/config.d.ts +2 -0
- package/dist/config.js +1 -0
- package/dist/copy-DXnzXsJa.d.ts +162 -0
- package/dist/copy-DXnzXsJa.d.ts.map +1 -0
- package/dist/helpers-BPuPGjQP.js +61 -0
- package/dist/helpers-BPuPGjQP.js.map +1 -0
- package/dist/index.d.ts +24 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +188 -0
- package/dist/index.js.map +1 -0
- package/dist/inspector.d.ts +37 -0
- package/dist/inspector.d.ts.map +1 -0
- package/dist/inspector.js +572 -0
- package/dist/inspector.js.map +1 -0
- package/dist/react/index.d.ts +37 -0
- package/dist/react/index.d.ts.map +1 -0
- package/dist/react/index.js +86 -0
- package/dist/react/index.js.map +1 -0
- package/dist/sarif-CI8HOokm.js +1033 -0
- package/dist/sarif-CI8HOokm.js.map +1 -0
- package/dist/scan-Ch2BfIUD.js +2561 -0
- package/dist/scan-Ch2BfIUD.js.map +1 -0
- package/dist/tools.d.ts +377 -0
- package/dist/tools.d.ts.map +1 -0
- package/dist/tools.js +4 -0
- package/dist/vite.d.ts +24 -0
- package/dist/vite.d.ts.map +1 -0
- package/dist/vite.js +264 -0
- package/dist/vite.js.map +1 -0
- package/package.json +148 -15
- package/src/cli.ts +528 -0
- package/src/index.ts +31 -0
- package/src/inspector-dialog.ts +450 -0
- package/src/inspector.ts +228 -0
- package/src/react/index.tsx +112 -0
- package/src/runtime/copy.ts +221 -0
- package/src/runtime/helpers.ts +66 -0
- package/src/runtime/locale.ts +49 -0
- package/src/runtime/types.ts +106 -0
- package/src/tools/catalog.ts +449 -0
- package/src/tools/compile.ts +121 -0
- package/src/tools/config.ts +211 -0
- package/src/tools/diff.ts +84 -0
- package/src/tools/entry.ts +325 -0
- package/src/tools/extract.ts +694 -0
- package/src/tools/generate.ts +257 -0
- package/src/tools/icu.ts +211 -0
- package/src/tools/index.ts +91 -0
- package/src/tools/lint.ts +865 -0
- package/src/tools/lock.ts +95 -0
- package/src/tools/mf1.ts +246 -0
- package/src/tools/mf2.ts +752 -0
- package/src/tools/migrate.ts +138 -0
- package/src/tools/presets.ts +159 -0
- package/src/tools/pseudo.ts +40 -0
- package/src/tools/sarif.ts +80 -0
- package/src/tools/scan.ts +303 -0
- package/src/tools/syntax.ts +24 -0
- package/src/tools/types.ts +137 -0
- package/src/vite.ts +296 -0
- package/index.js +0 -1
|
@@ -0,0 +1,517 @@
|
|
|
1
|
+
import { MessageFormatElement } from "@formatjs/icu-messageformat-parser";
|
|
2
|
+
interface Translation {
|
|
3
|
+
text: string;
|
|
4
|
+
ast: MessageFormatElement[];
|
|
5
|
+
file: string;
|
|
6
|
+
}
|
|
7
|
+
interface Message {
|
|
8
|
+
key: string;
|
|
9
|
+
/** The first segment of the key, which names its file. */
|
|
10
|
+
area: string;
|
|
11
|
+
file: string;
|
|
12
|
+
kind?: string;
|
|
13
|
+
surface?: string;
|
|
14
|
+
/** One sentence telling a translator where the string appears. */
|
|
15
|
+
context?: string;
|
|
16
|
+
/** What each placeholder holds, keyed by argument name. */
|
|
17
|
+
argDocs: Map<string, string>;
|
|
18
|
+
/** Completes something beside it rather than standing as a sentence, so sentence rules do not apply. */
|
|
19
|
+
fragment: boolean;
|
|
20
|
+
/** Lint rules the entry is exempt from, each with the reason. */
|
|
21
|
+
allow: Map<string, string>;
|
|
22
|
+
/** A change someone asked for, left for whoever edits the entry next, and deleted once it is made. */
|
|
23
|
+
comment?: string;
|
|
24
|
+
/** Asked to go: the entry, its translations and the code that reads it. */
|
|
25
|
+
remove: boolean;
|
|
26
|
+
/** The source message, in ICU MessageFormat. */
|
|
27
|
+
text: string;
|
|
28
|
+
ast: MessageFormatElement[];
|
|
29
|
+
/** Argument name to TypeScript type. */
|
|
30
|
+
args: Map<string, string>;
|
|
31
|
+
/** How each formatted argument is styled, for the doc comment at the call site. */
|
|
32
|
+
argFormats: Map<string, string>;
|
|
33
|
+
tags: string[];
|
|
34
|
+
/** Translations by locale. */
|
|
35
|
+
translations: Map<string, Translation>;
|
|
36
|
+
}
|
|
37
|
+
interface Problem {
|
|
38
|
+
severity: 'error' | 'warn';
|
|
39
|
+
/** Relative to the project root; none for a problem that isn't in a file. */
|
|
40
|
+
file?: string;
|
|
41
|
+
/** The entry it is about, in `file`; none for the file as a whole. */
|
|
42
|
+
key?: string;
|
|
43
|
+
message: string;
|
|
44
|
+
}
|
|
45
|
+
/** `file key`, as the CLI names where a problem is. */
|
|
46
|
+
declare function whereOf(problem: Problem): string;
|
|
47
|
+
interface Catalog {
|
|
48
|
+
messages: Message[];
|
|
49
|
+
/** The translated locales found under `locales`, without the source. */
|
|
50
|
+
locales: string[];
|
|
51
|
+
problems: Problem[];
|
|
52
|
+
}
|
|
53
|
+
declare class CatalogError extends Error {
|
|
54
|
+
readonly problems: Problem[];
|
|
55
|
+
constructor(problems: Problem[]);
|
|
56
|
+
}
|
|
57
|
+
/**
|
|
58
|
+
* A key is dotted lowercase, two segments at least, and its first segment names the file it lives
|
|
59
|
+
* in. Keys are read at every call site, so they say what the string is for: `cart.checkout.title`.
|
|
60
|
+
*/
|
|
61
|
+
declare const KEY_PATTERN: RegExp;
|
|
62
|
+
/**
|
|
63
|
+
* Loads and checks the catalog. Throws a `CatalogError` when anything is an error; warnings ride along.
|
|
64
|
+
* `unsaved` holds file contents by absolute path to read in place of what is on disk, so an edit can be
|
|
65
|
+
* checked before it is written; a translation file in it that isn't on disk yet is read too.
|
|
66
|
+
*/
|
|
67
|
+
declare function loadCatalog(config: ResolvedConfig, unsaved?: ReadonlyMap<string, string>): Catalog;
|
|
68
|
+
interface EntryLocation {
|
|
69
|
+
/** Absolute. */
|
|
70
|
+
file: string;
|
|
71
|
+
/** From 1. */
|
|
72
|
+
line: number;
|
|
73
|
+
/** From 1. */
|
|
74
|
+
column: number;
|
|
75
|
+
}
|
|
76
|
+
/**
|
|
77
|
+
* Where a message's entry is written: its translation in `locale` when there is one, else the catalog.
|
|
78
|
+
* Read from the file as it is now, so an entry moved since the catalog was loaded is still found.
|
|
79
|
+
*/
|
|
80
|
+
declare function entryLocation(config: ResolvedConfig, message: Message, locale?: string): EntryLocation;
|
|
81
|
+
/** The source message as a reader sees it with no placeholders filled: for docs and reports. */
|
|
82
|
+
declare function previewOf(message: Message): string;
|
|
83
|
+
/**
|
|
84
|
+
* The defaults: four kinds of string, the surfaces they sit on, and the word lists of the strict lint preset.
|
|
85
|
+
*
|
|
86
|
+
* The kinds are the four any UI writing guide comes down to. A name identifies, an action says what
|
|
87
|
+
* pressing it does, a description adds what the name cannot carry, a state reports what is true.
|
|
88
|
+
* Each carries a budget and a grammar, which is what makes a mechanical check of the words possible.
|
|
89
|
+
*/
|
|
90
|
+
type Severity = 'error' | 'warn' | 'off';
|
|
91
|
+
interface KindRule {
|
|
92
|
+
/** What the kind is for, shown when an editor completes it. */
|
|
93
|
+
doc: string;
|
|
94
|
+
/** The most words it may have. Articles, short prepositions and asides in parentheses are free. */
|
|
95
|
+
maxWords?: number;
|
|
96
|
+
/** The most sentences it may have, and per surface where that differs. */
|
|
97
|
+
maxSentences?: number;
|
|
98
|
+
maxSentencesOn?: Record<string, number>;
|
|
99
|
+
/** Whether it ends with a period: always, never, or only on the surfaces listed. */
|
|
100
|
+
period?: 'always' | 'never' | string[];
|
|
101
|
+
/** Capitalizes only its first word and proper nouns. */
|
|
102
|
+
sentenceCase?: boolean;
|
|
103
|
+
/** Carries no explanation after a dash or colon: `Quick capture`, not `Quick capture: choose an area`. */
|
|
104
|
+
bare?: boolean;
|
|
105
|
+
}
|
|
106
|
+
declare const DEFAULT_KINDS: Record<string, KindRule>;
|
|
107
|
+
declare const DEFAULT_SURFACES: Record<string, string>;
|
|
108
|
+
/** The word lists of the strict preset: filler, marketing and reassurance, and American spelling. */
|
|
109
|
+
declare const STRICT_LISTS: {
|
|
110
|
+
banned: {
|
|
111
|
+
words: string[];
|
|
112
|
+
why: string;
|
|
113
|
+
}[];
|
|
114
|
+
spelling: Record<string, string>;
|
|
115
|
+
};
|
|
116
|
+
/** What a rule is given about one message in one locale. */
|
|
117
|
+
interface RuleContext {
|
|
118
|
+
/** The entry, as the source catalog has it. */
|
|
119
|
+
message: Message;
|
|
120
|
+
/** The locale read: the source, or a translation's. */
|
|
121
|
+
locale: string;
|
|
122
|
+
/** The message in that locale. */
|
|
123
|
+
ast: MessageFormatElement[];
|
|
124
|
+
/** The shape the message's kind is held to, when it names a kind the config defines. */
|
|
125
|
+
kind: KindRule | undefined;
|
|
126
|
+
/** The message in that locale, as prose. */
|
|
127
|
+
text: Readings;
|
|
128
|
+
/** The source message as prose, to hold a translation to it: `text` itself in the source locale. */
|
|
129
|
+
source: Readings;
|
|
130
|
+
config: ResolvedConfig;
|
|
131
|
+
}
|
|
132
|
+
interface RuleBase {
|
|
133
|
+
/** One sentence: what the rule holds a string to. */
|
|
134
|
+
description: string;
|
|
135
|
+
/** Its severity under `extends: 'recommended'`; off when unset. */
|
|
136
|
+
recommended?: Severity;
|
|
137
|
+
/** Its severity under `extends: 'strict'`; `error` when unset. */
|
|
138
|
+
strict?: Severity;
|
|
139
|
+
/**
|
|
140
|
+
* Only entries of these kinds, on these surfaces, or in these areas (a key's first segment); an
|
|
141
|
+
* entry that says no kind or surface is skipped by a rule that names some. Only the source unless
|
|
142
|
+
* `locale` says otherwise, since most writing rules are written for one language: `all` reads
|
|
143
|
+
* every locale, and a list those languages and their regions (`de` covers `de-CH`).
|
|
144
|
+
*/
|
|
145
|
+
on?: {
|
|
146
|
+
kind?: string[];
|
|
147
|
+
surface?: string[];
|
|
148
|
+
area?: string[];
|
|
149
|
+
locale?: 'all' | string[];
|
|
150
|
+
};
|
|
151
|
+
}
|
|
152
|
+
/** A rule written as code. */
|
|
153
|
+
interface CheckRule extends RuleBase {
|
|
154
|
+
/** What is wrong with the message, a sentence each that states the fix; none when it passes. */
|
|
155
|
+
check(context: RuleContext): (string | Report)[];
|
|
156
|
+
}
|
|
157
|
+
/** A finding that can say where it is, and what to write instead. */
|
|
158
|
+
interface Report {
|
|
159
|
+
message: string;
|
|
160
|
+
/** The words the finding is about, as a reading has them: found in the message's text, in any case. */
|
|
161
|
+
match?: string;
|
|
162
|
+
/** What `prosebook lint --fix` writes in place of `match`, wherever it stands; its case follows the text's. */
|
|
163
|
+
fix?: string;
|
|
164
|
+
}
|
|
165
|
+
/** A replacement in a message's text, by offset. */
|
|
166
|
+
interface Edit {
|
|
167
|
+
start: number;
|
|
168
|
+
end: number;
|
|
169
|
+
text: string;
|
|
170
|
+
}
|
|
171
|
+
/** Words or patterns a string never uses. */
|
|
172
|
+
interface ExistenceRule extends RuleBase {
|
|
173
|
+
type: 'existence';
|
|
174
|
+
/** Words or phrases, matched whole and in any case. `{match}` is the one listed. */
|
|
175
|
+
words?: string[];
|
|
176
|
+
/** `{match}` is the text matched. */
|
|
177
|
+
patterns?: string[];
|
|
178
|
+
ignoreCase?: boolean;
|
|
179
|
+
message: string;
|
|
180
|
+
}
|
|
181
|
+
/** A word or phrase the product writes another way. */
|
|
182
|
+
interface SubstitutionRule extends RuleBase {
|
|
183
|
+
type: 'substitution';
|
|
184
|
+
/** A word or phrase, matched whole and in any case, and the one written instead. */
|
|
185
|
+
swap: Record<string, string>;
|
|
186
|
+
/** `{match}` and `{use}`; `"{match}" is written "{use}"` when unset. */
|
|
187
|
+
message?: string;
|
|
188
|
+
}
|
|
189
|
+
/** A budget, beside the one a kind sets: per surface, say, or in characters. */
|
|
190
|
+
interface OccurrenceRule extends RuleBase {
|
|
191
|
+
type: 'occurrence';
|
|
192
|
+
/** Every word, placeholders included; sentences; or characters, placeholders not included. */
|
|
193
|
+
count: 'words' | 'sentences' | 'characters';
|
|
194
|
+
max?: number;
|
|
195
|
+
min?: number;
|
|
196
|
+
/** `max` and `min` are multiples of the source's count: `max: 1.4` is 40% longer than the source at most. */
|
|
197
|
+
relative?: boolean;
|
|
198
|
+
/** `{count}`, `{max}`, `{min}`, and with `relative`, `{source}` (the source's count) and `{limit}`. */
|
|
199
|
+
message?: string;
|
|
200
|
+
}
|
|
201
|
+
interface CapitalizationRule extends RuleBase {
|
|
202
|
+
type: 'capitalization';
|
|
203
|
+
/** `sentence` capitalizes only the first word and proper nouns, `title` every word but short function words. */
|
|
204
|
+
case: 'sentence' | 'title' | 'lower' | 'upper';
|
|
205
|
+
/** Words that keep their case, beside `lint.properNouns`. */
|
|
206
|
+
exceptions?: string[];
|
|
207
|
+
/** `{match}` is the first word out of case. */
|
|
208
|
+
message?: string;
|
|
209
|
+
}
|
|
210
|
+
/** A string that matches `when` (every string, when unset) matches `require` too. */
|
|
211
|
+
interface ConditionalRule extends RuleBase {
|
|
212
|
+
type: 'conditional';
|
|
213
|
+
when?: string;
|
|
214
|
+
require: string;
|
|
215
|
+
ignoreCase?: boolean;
|
|
216
|
+
/** `{match}` is the text `when` matched. */
|
|
217
|
+
message: string;
|
|
218
|
+
}
|
|
219
|
+
type Rule = CheckRule | ExistenceRule | SubstitutionRule | OccurrenceRule | CapitalizationRule | ConditionalRule;
|
|
220
|
+
/** A set of rules, named `<name>/<rule>` in `lint.rules` and in an entry's `allow`. */
|
|
221
|
+
interface Plugin {
|
|
222
|
+
name: string;
|
|
223
|
+
rules: Record<string, Rule>;
|
|
224
|
+
}
|
|
225
|
+
/** Typed plugin, for `lint.plugins`. */
|
|
226
|
+
declare function definePlugin(plugin: Plugin): Plugin;
|
|
227
|
+
interface Finding {
|
|
228
|
+
key: string;
|
|
229
|
+
/** The catalog file, or for a translation, the locale's file. */
|
|
230
|
+
file: string;
|
|
231
|
+
/** The locale whose text the finding is about; the source for an `allow` finding. */
|
|
232
|
+
locale: string;
|
|
233
|
+
/** The rule's name, or `allow` for an exemption that is itself wrong. */
|
|
234
|
+
rule: string;
|
|
235
|
+
severity: Exclude<Severity, 'off'>;
|
|
236
|
+
message: string;
|
|
237
|
+
/** Where in the locale's message text, when the rule named a match and it is written there as read. */
|
|
238
|
+
at?: {
|
|
239
|
+
start: number;
|
|
240
|
+
end: number;
|
|
241
|
+
};
|
|
242
|
+
/** The edits that fix it, at every place the match stands. */
|
|
243
|
+
fix?: Edit[];
|
|
244
|
+
}
|
|
245
|
+
/** Stands in for a placeholder in a reading, which no prose rule reads. */
|
|
246
|
+
declare const HOLE = "";
|
|
247
|
+
/** The message as prose: placeholders and verbatim tags read as `HOLE`, and `’` as `'` in `variants`. */
|
|
248
|
+
interface Readings {
|
|
249
|
+
/** Every `other` arm taken: what a budget is measured on. */
|
|
250
|
+
primary: string;
|
|
251
|
+
/** One reading per arm, so a word hidden in `one` is still found. */
|
|
252
|
+
variants: string[];
|
|
253
|
+
/** Only the words the message always carries. */
|
|
254
|
+
skeleton: string;
|
|
255
|
+
}
|
|
256
|
+
/** The words a budget counts: articles, short prepositions and asides in parentheses are free. */
|
|
257
|
+
declare function words(text: string): string[];
|
|
258
|
+
declare function sentences(text: string): number;
|
|
259
|
+
/** A word or phrase on its own, not inside a longer word or a hyphenated compound. */
|
|
260
|
+
declare function phrase(p: string): RegExp;
|
|
261
|
+
/**
|
|
262
|
+
* The singular of an English plural noun, or nothing where it doesn't look like one. A word with no
|
|
263
|
+
* vowel is a unit or an abbreviation (`kbps`, `fps`, `hrs`), which reads the same after 1.
|
|
264
|
+
*/
|
|
265
|
+
declare function singularOf(word: string): string | undefined;
|
|
266
|
+
declare const CORE_RULES: {
|
|
267
|
+
whitespace: {
|
|
268
|
+
description: string;
|
|
269
|
+
recommended: "error";
|
|
270
|
+
on: {
|
|
271
|
+
locale: "all";
|
|
272
|
+
};
|
|
273
|
+
check: ({ text }: RuleContext) => string[] | {
|
|
274
|
+
message: string;
|
|
275
|
+
match: string;
|
|
276
|
+
fix: string;
|
|
277
|
+
}[];
|
|
278
|
+
};
|
|
279
|
+
'word-budget': {
|
|
280
|
+
description: string;
|
|
281
|
+
recommended: "warn";
|
|
282
|
+
check: ({ message: m, kind, text }: RuleContext) => string[];
|
|
283
|
+
};
|
|
284
|
+
'sentence-budget': {
|
|
285
|
+
description: string;
|
|
286
|
+
recommended: "warn";
|
|
287
|
+
check: ({ message: m, kind, text }: RuleContext) => string[];
|
|
288
|
+
};
|
|
289
|
+
period: {
|
|
290
|
+
description: string;
|
|
291
|
+
recommended: "warn";
|
|
292
|
+
check: ({ message: m, kind, text }: RuleContext) => string[];
|
|
293
|
+
};
|
|
294
|
+
'no-period': {
|
|
295
|
+
description: string;
|
|
296
|
+
recommended: "warn";
|
|
297
|
+
check: ({ message: m, kind, text }: RuleContext) => string[];
|
|
298
|
+
};
|
|
299
|
+
'bare-name': {
|
|
300
|
+
description: string;
|
|
301
|
+
recommended: "warn";
|
|
302
|
+
check: ({ message: m, kind, text }: RuleContext) => string[];
|
|
303
|
+
};
|
|
304
|
+
'sentence-case': {
|
|
305
|
+
description: string;
|
|
306
|
+
check: ({ message: m, kind, text, config }: RuleContext) => {
|
|
307
|
+
message: string;
|
|
308
|
+
match: string;
|
|
309
|
+
}[];
|
|
310
|
+
};
|
|
311
|
+
'banned-word': {
|
|
312
|
+
description: string;
|
|
313
|
+
recommended: "warn";
|
|
314
|
+
check: ({ text, config }: RuleContext) => {
|
|
315
|
+
message: string;
|
|
316
|
+
match: string;
|
|
317
|
+
}[];
|
|
318
|
+
};
|
|
319
|
+
spelling: {
|
|
320
|
+
description: string;
|
|
321
|
+
recommended: "warn";
|
|
322
|
+
check: ({ text, config: { lint } }: RuleContext) => {
|
|
323
|
+
message: string;
|
|
324
|
+
match: string;
|
|
325
|
+
fix: string | undefined;
|
|
326
|
+
}[];
|
|
327
|
+
};
|
|
328
|
+
'one-word': {
|
|
329
|
+
description: string;
|
|
330
|
+
recommended: "warn";
|
|
331
|
+
check: ({ text, config: { lint } }: RuleContext) => {
|
|
332
|
+
message: string;
|
|
333
|
+
match: string;
|
|
334
|
+
fix: string | undefined;
|
|
335
|
+
}[];
|
|
336
|
+
};
|
|
337
|
+
'no-em-dash': {
|
|
338
|
+
description: string;
|
|
339
|
+
check: ({ text }: RuleContext) => {
|
|
340
|
+
message: string;
|
|
341
|
+
match: string;
|
|
342
|
+
}[];
|
|
343
|
+
};
|
|
344
|
+
path: {
|
|
345
|
+
description: string;
|
|
346
|
+
check: ({ text, config }: RuleContext) => {
|
|
347
|
+
message: string;
|
|
348
|
+
match: string;
|
|
349
|
+
fix: string;
|
|
350
|
+
}[];
|
|
351
|
+
};
|
|
352
|
+
contractions: {
|
|
353
|
+
description: string;
|
|
354
|
+
check: ({ text }: RuleContext) => {
|
|
355
|
+
message: string;
|
|
356
|
+
match: string;
|
|
357
|
+
fix: string;
|
|
358
|
+
}[];
|
|
359
|
+
};
|
|
360
|
+
ellipsis: {
|
|
361
|
+
description: string;
|
|
362
|
+
on: {
|
|
363
|
+
locale: "all";
|
|
364
|
+
};
|
|
365
|
+
check: ({ text }: RuleContext) => {
|
|
366
|
+
message: string;
|
|
367
|
+
match: string;
|
|
368
|
+
fix: string;
|
|
369
|
+
}[];
|
|
370
|
+
};
|
|
371
|
+
'plural-count': {
|
|
372
|
+
description: string;
|
|
373
|
+
recommended: "warn";
|
|
374
|
+
check: ({ ast }: RuleContext) => Report[];
|
|
375
|
+
};
|
|
376
|
+
'plural-one': {
|
|
377
|
+
description: string;
|
|
378
|
+
recommended: "warn";
|
|
379
|
+
on: {
|
|
380
|
+
locale: "all";
|
|
381
|
+
};
|
|
382
|
+
check: ({ ast, locale, config }: RuleContext) => Report[];
|
|
383
|
+
};
|
|
384
|
+
'arm-endings': {
|
|
385
|
+
description: string;
|
|
386
|
+
recommended: "warn";
|
|
387
|
+
on: {
|
|
388
|
+
locale: "all";
|
|
389
|
+
};
|
|
390
|
+
check: ({ ast }: RuleContext) => string[];
|
|
391
|
+
};
|
|
392
|
+
'formatted-by-hand': {
|
|
393
|
+
description: string;
|
|
394
|
+
recommended: "warn";
|
|
395
|
+
on: {
|
|
396
|
+
locale: "all";
|
|
397
|
+
};
|
|
398
|
+
check: ({ ast, text }: RuleContext) => Report[];
|
|
399
|
+
};
|
|
400
|
+
'source-ending': {
|
|
401
|
+
description: string;
|
|
402
|
+
recommended: "warn";
|
|
403
|
+
on: {
|
|
404
|
+
locale: "all";
|
|
405
|
+
};
|
|
406
|
+
check: ({ text, source }: RuleContext) => string[];
|
|
407
|
+
};
|
|
408
|
+
};
|
|
409
|
+
type CoreRule = keyof typeof CORE_RULES;
|
|
410
|
+
/** A rule as code, checked once when the config loads: a JSON config is not type-checked. */
|
|
411
|
+
declare function compileRule(name: string, rule: Rule): CheckRule;
|
|
412
|
+
/** `text` with the edits made, leaving out any that overlaps one before it. */
|
|
413
|
+
declare function applyEdits(text: string, edits: Edit[]): string;
|
|
414
|
+
declare function lint(messages: Message[], config: ResolvedConfig): Finding[];
|
|
415
|
+
interface WordLists {
|
|
416
|
+
/** Words a string never uses, in groups that say why. */
|
|
417
|
+
banned?: {
|
|
418
|
+
words: string[];
|
|
419
|
+
why: string;
|
|
420
|
+
}[];
|
|
421
|
+
/** A spelling, and the one the product uses instead. */
|
|
422
|
+
spelling?: Record<string, string>;
|
|
423
|
+
/** A near-synonym, and the one word the product uses for that concept. */
|
|
424
|
+
concepts?: Record<string, string>;
|
|
425
|
+
/** Words that keep their capital inside a sentence-case string: product names, platforms. */
|
|
426
|
+
properNouns?: string[];
|
|
427
|
+
/** What a path through menus or settings is written with, spaced: `›` by default, as in Settings › General. */
|
|
428
|
+
pathSeparator?: string;
|
|
429
|
+
}
|
|
430
|
+
type RuleSeverities = Partial<Record<CoreRule, Severity>> & Record<string, Severity>;
|
|
431
|
+
interface LintConfig extends WordLists {
|
|
432
|
+
/** `recommended` (the default) checks shape; `strict` adds the word lists and rules of a house style guide. */
|
|
433
|
+
extends?: 'recommended' | 'strict' | 'none';
|
|
434
|
+
/** Rules of your own, as `<plugin>/<rule>`. Each takes the severity it gives itself under `extends`. */
|
|
435
|
+
plugins?: Plugin[];
|
|
436
|
+
rules?: RuleSeverities;
|
|
437
|
+
/** Severities for one area's entries (a key's first segment) over `rules`: `{ native: { 'sentence-case': 'off' } }`. */
|
|
438
|
+
areas?: Record<string, RuleSeverities>;
|
|
439
|
+
}
|
|
440
|
+
interface ProsebookConfig {
|
|
441
|
+
/** The source-language catalog: one `<area>.yaml` per area. */
|
|
442
|
+
catalog?: string;
|
|
443
|
+
/** Translations: `<locale>/<area>.yaml` or `<locale>.yaml`, holding `key: message`. */
|
|
444
|
+
locales?: string;
|
|
445
|
+
/** Where the generated modules go. */
|
|
446
|
+
out?: string;
|
|
447
|
+
/** Records which source text each translation was made from, so a changed source marks it stale. */
|
|
448
|
+
lock?: string;
|
|
449
|
+
/** The locale the catalog is written in. Its code is also the field holding the message. */
|
|
450
|
+
source?: string;
|
|
451
|
+
/**
|
|
452
|
+
* The syntax messages are written in: ICU MessageFormat (1) or Unicode MessageFormat 2. Source and
|
|
453
|
+
* translations alike; `prosebook migrate` rewrites a catalog from one to the other.
|
|
454
|
+
*/
|
|
455
|
+
messageFormat?: 1 | 2;
|
|
456
|
+
/** Locales that ship in the main bundle beside the source, rather than loading when first used. */
|
|
457
|
+
bundled?: string[];
|
|
458
|
+
/** A pseudo-locale generated from the source (accented and lengthened) to find layout bugs and hardcoded text. */
|
|
459
|
+
pseudo?: string | false;
|
|
460
|
+
/** What a translation whose source changed since does: still show (`use`) or show the source (`fallback`). */
|
|
461
|
+
stale?: 'use' | 'fallback';
|
|
462
|
+
/** Generated modules as TypeScript or as JavaScript with a `.d.ts` beside the index. */
|
|
463
|
+
language?: 'ts' | 'js';
|
|
464
|
+
/** The extension generated imports name: `.js` suits most TypeScript setups, `.ts` suits Node's type stripping. */
|
|
465
|
+
importExtension?: '.js' | '.ts' | '';
|
|
466
|
+
/** The fields every entry must have. A shorthand `key: message` entry satisfies none of them. */
|
|
467
|
+
require?: ('context' | 'kind' | 'surface')[];
|
|
468
|
+
/** The kinds of string an entry may say it is, with the shape each one is held to. */
|
|
469
|
+
kinds?: Record<string, KindRule>;
|
|
470
|
+
/** Where a string may sit, with what each surface means. */
|
|
471
|
+
surfaces?: Record<string, string>;
|
|
472
|
+
lint?: LintConfig;
|
|
473
|
+
/** Where `prosebook scan` looks for hardcoded text and catalog keys. */
|
|
474
|
+
scan?: {
|
|
475
|
+
dirs?: string[];
|
|
476
|
+
extensions?: string[];
|
|
477
|
+
/** JSX attributes whose literal value a person reads. */
|
|
478
|
+
attributes?: string[];
|
|
479
|
+
};
|
|
480
|
+
}
|
|
481
|
+
interface ResolvedConfig {
|
|
482
|
+
root: string;
|
|
483
|
+
catalog: string;
|
|
484
|
+
locales: string;
|
|
485
|
+
out: string;
|
|
486
|
+
lock: string;
|
|
487
|
+
source: string;
|
|
488
|
+
messageFormat: 1 | 2;
|
|
489
|
+
bundled: string[];
|
|
490
|
+
pseudo: string | false;
|
|
491
|
+
stale: 'use' | 'fallback';
|
|
492
|
+
language: 'ts' | 'js';
|
|
493
|
+
importExtension: '.js' | '.ts' | '';
|
|
494
|
+
require: ('context' | 'kind' | 'surface')[];
|
|
495
|
+
kinds: Record<string, KindRule>;
|
|
496
|
+
surfaces: Record<string, string>;
|
|
497
|
+
lint: {
|
|
498
|
+
rules: Record<string, {
|
|
499
|
+
rule: CheckRule;
|
|
500
|
+
severity: Severity;
|
|
501
|
+
}>;
|
|
502
|
+
areas: Record<string, Record<string, Severity>>;
|
|
503
|
+
} & Required<WordLists>;
|
|
504
|
+
scan: {
|
|
505
|
+
dirs: string[];
|
|
506
|
+
extensions: string[];
|
|
507
|
+
attributes: string[];
|
|
508
|
+
};
|
|
509
|
+
}
|
|
510
|
+
/** Typed config, for `prosebook.config.ts`. */
|
|
511
|
+
declare function defineConfig(config: ProsebookConfig): ProsebookConfig;
|
|
512
|
+
declare const CONFIG_FILES: string[];
|
|
513
|
+
/** Finds and reads the config at `root`, or the defaults when there is none. */
|
|
514
|
+
declare function loadConfig(root: string, inline?: ProsebookConfig): Promise<ResolvedConfig>;
|
|
515
|
+
declare function resolveConfig(root: string, config: ProsebookConfig): ResolvedConfig;
|
|
516
|
+
export { sentences as A, EntryLocation as B, RuleContext as C, definePlugin as D, compileRule as E, KindRule as F, entryLocation as G, Message as H, STRICT_LISTS as I, whereOf as J, loadCatalog as K, Severity as L, words as M, DEFAULT_KINDS as N, lint as O, DEFAULT_SURFACES as P, Catalog as R, Rule as S, applyEdits as T, Problem as U, KEY_PATTERN as V, Translation as W, MessageFormatElement as Y, HOLE as _, WordLists as a, Readings as b, resolveConfig as c, CheckRule as d, ConditionalRule as f, Finding as g, ExistenceRule as h, ResolvedConfig as i, singularOf as j, phrase as k, CORE_RULES as l, Edit as m, LintConfig as n, defineConfig as o, CoreRule as p, previewOf as q, ProsebookConfig as r, loadConfig as s, CONFIG_FILES as t, CapitalizationRule as u, OccurrenceRule as v, SubstitutionRule as w, Report as x, Plugin as y, CatalogError as z };
|
|
517
|
+
//# sourceMappingURL=config-_4HfnJQu.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"config-_4HfnJQu.d.ts","names":[],"sources":["../src/tools/catalog.ts","../src/tools/presets.ts","../src/tools/lint.ts","../src/tools/config.ts"],"mappings":"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"}
|
package/dist/config.d.ts
ADDED
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
import { A as sentences, C as RuleContext, D as definePlugin, F as KindRule, L as Severity, M as words, S as Rule, _ as HOLE, a as WordLists, b as Readings, c as resolveConfig, d as CheckRule, f as ConditionalRule, h as ExistenceRule, i as ResolvedConfig, k as phrase, n as LintConfig, o as defineConfig, r as ProsebookConfig, s as loadConfig, t as CONFIG_FILES, u as CapitalizationRule, v as OccurrenceRule, w as SubstitutionRule, x as Report, y as Plugin } from "./config-_4HfnJQu.js";
|
|
2
|
+
export { CONFIG_FILES, type CapitalizationRule, type CheckRule, type ConditionalRule, type ExistenceRule, HOLE, type KindRule, LintConfig, type OccurrenceRule, type Plugin, ProsebookConfig, type Readings, type Report, ResolvedConfig, type Rule, type RuleContext, type Severity, type SubstitutionRule, WordLists, defineConfig, definePlugin, loadConfig, phrase, resolveConfig, sentences, words };
|
package/dist/config.js
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export { t as CONFIG_FILES, l as HOLE, n as defineConfig, f as definePlugin, r as loadConfig, m as phrase, i as resolveConfig, h as sentences, _ as words } from "./config-D--RITk2.js";
|