@useinsider/eslint-config 4.0.0-beta.1 → 4.0.0-beta.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/README.md +100 -9
- package/dist/builders/scopeBlocks.d.ts +6 -0
- package/dist/cli.cjs +551 -166
- package/dist/cli.cjs.map +1 -1
- package/dist/main.cjs +390 -84
- package/dist/main.cjs.map +1 -1
- package/dist/main.js +391 -85
- package/dist/main.js.map +1 -1
- package/dist/utils/ensureConfigStructure.d.ts +8 -4
- package/dist/utils/ensureOxlintConfig.d.ts +2 -1
- package/dist/utils/layoutDiagnosis.d.ts +63 -0
- package/dist/utils/offerMigration.d.ts +42 -0
- package/package.json +1 -1
|
@@ -1,4 +1,6 @@
|
|
|
1
1
|
import { type TSESTree } from '@typescript-eslint/types';
|
|
2
|
+
import { ESLINT_CONFIG_FILENAMES, type LayoutDiagnosis, LINT_MODULE_FILENAMES } from './layoutDiagnosis';
|
|
3
|
+
import { offerMigration } from './offerMigration';
|
|
2
4
|
export interface ConfigStructureViolation {
|
|
3
5
|
line: number;
|
|
4
6
|
column: number;
|
|
@@ -8,8 +10,7 @@ export interface ValidateProgramStructureOptions {
|
|
|
8
10
|
isInsiderImportSource?: (source: string, configPath: string) => boolean;
|
|
9
11
|
expectedCallee?: string;
|
|
10
12
|
}
|
|
11
|
-
export
|
|
12
|
-
export declare const ESLINT_CONFIG_FILENAMES: readonly string[];
|
|
13
|
+
export { ESLINT_CONFIG_FILENAMES, LINT_MODULE_FILENAMES };
|
|
13
14
|
export declare function defaultIsInsiderImportSource(source: string, configPath: string): boolean;
|
|
14
15
|
export declare function validateProgramStructure(program: TSESTree.Program, configPath?: string, options?: ValidateProgramStructureOptions): ConfigStructureViolation[];
|
|
15
16
|
export declare function validateLintModuleStructure(program: TSESTree.Program, configPath?: string, options?: ValidateProgramStructureOptions): ConfigStructureViolation[];
|
|
@@ -28,5 +29,8 @@ export declare function captureConsumerConfigDir(configPath: string | null): voi
|
|
|
28
29
|
* getConsumerConfigDir(); // '/repo'
|
|
29
30
|
*/
|
|
30
31
|
export declare function getConsumerConfigDir(): string;
|
|
31
|
-
export
|
|
32
|
-
|
|
32
|
+
export interface RunValidationDeps {
|
|
33
|
+
diagnose?: (directory: string) => LayoutDiagnosis;
|
|
34
|
+
offer?: typeof offerMigration;
|
|
35
|
+
}
|
|
36
|
+
export declare function ensureConfigStructure(overridePath?: string | null, deps?: RunValidationDeps): void;
|
|
@@ -1,4 +1,5 @@
|
|
|
1
|
-
|
|
1
|
+
import { OXLINT_CONFIG_FILENAMES } from './layoutDiagnosis';
|
|
2
|
+
export { OXLINT_CONFIG_FILENAMES };
|
|
2
3
|
/**
|
|
3
4
|
* Fails when the consumer enabled the ESLint-side oxlint suppression without a sibling oxlint
|
|
4
5
|
* config to run the suppressed rules. Resolved against the directory
|
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
export declare const LINT_MODULE_FILENAMES: readonly string[];
|
|
2
|
+
export declare const ESLINT_CONFIG_FILENAMES: readonly string[];
|
|
3
|
+
export declare const OXLINT_CONFIG_FILENAMES: readonly string[];
|
|
4
|
+
export declare const OPT_OUT_ENV = "INSIDER_SKIP_CONFIG_VALIDATION";
|
|
5
|
+
export declare const MIGRATE_COMMAND = "npx @useinsider/eslint-config migrate";
|
|
6
|
+
export declare const SCAFFOLD_COMMAND = "npx @useinsider/eslint-config";
|
|
7
|
+
export declare const INSIDER_IMPORT_SOURCE = "@useinsider/eslint-config";
|
|
8
|
+
export declare const TARGET_CALLEE_NAME = "useInsider";
|
|
9
|
+
export declare const ESLINT_RENDERER_NAME = "useInsiderESLint";
|
|
10
|
+
export declare const OXC_RENDERER_NAME = "useInsiderOXC";
|
|
11
|
+
export declare const RENDERER_EXPORT = "export const { useInsiderESLint, useInsiderOXC } = useInsider({ ... })";
|
|
12
|
+
export declare const EXPECTED_LAYOUT: string;
|
|
13
|
+
export type LayoutCase = 'complete' | 'noConfig' | 'partial' | 'unmigratedV3';
|
|
14
|
+
export interface LayoutDiagnosis {
|
|
15
|
+
kind: LayoutCase;
|
|
16
|
+
directory: string;
|
|
17
|
+
lintModule: string | null;
|
|
18
|
+
eslintConfig: string | null;
|
|
19
|
+
oxlintConfig: string | null;
|
|
20
|
+
missing: string[];
|
|
21
|
+
autoMigratable: boolean;
|
|
22
|
+
}
|
|
23
|
+
export interface DiagnoseLayoutOptions {
|
|
24
|
+
fileExists?: (path: string) => boolean;
|
|
25
|
+
readSource?: (path: string) => string;
|
|
26
|
+
}
|
|
27
|
+
/**
|
|
28
|
+
* Whether a flat-config source is still the removed v3 shape: it imports `useInsider` and calls it
|
|
29
|
+
* itself, instead of importing a renderer from a sibling `insider.lint.*` module. Both the plain
|
|
30
|
+
* `export default useInsider({...})` form and the spread form are recognized.
|
|
31
|
+
* @example
|
|
32
|
+
* isV3EslintConfigSource("import { useInsider } from '@useinsider/eslint-config';\nexport default useInsider({});");
|
|
33
|
+
* // true
|
|
34
|
+
*/
|
|
35
|
+
export declare function isV3EslintConfigSource(source: string): boolean;
|
|
36
|
+
/**
|
|
37
|
+
* What of the three-file layout is on disk in a directory, and which of the four guidance branches
|
|
38
|
+
* applies. `unmigratedV3` is the only branch the in-lint migration offer acts on, because it is the
|
|
39
|
+
* only one {@link import('../cli/migrate').runMigrate} can actually rewrite.
|
|
40
|
+
* @example
|
|
41
|
+
* diagnoseLayout('/repo').kind; // 'unmigratedV3' when eslint.config.js still calls useInsider()
|
|
42
|
+
*/
|
|
43
|
+
export declare function diagnoseLayout(directory: string, options?: DiagnoseLayoutOptions): LayoutDiagnosis;
|
|
44
|
+
/**
|
|
45
|
+
* Import specifier for the consumer's lint module, naming the extension that is actually on disk so
|
|
46
|
+
* the suggested snippet resolves as printed.
|
|
47
|
+
* @example
|
|
48
|
+
* lintModuleSpecifier('/repo'); // './insider.lint.mts' when that is the file present
|
|
49
|
+
*/
|
|
50
|
+
export declare function lintModuleSpecifier(directory: string, fileExists?: (path: string) => boolean): string;
|
|
51
|
+
export interface LayoutGuidanceInput {
|
|
52
|
+
headline: string;
|
|
53
|
+
diagnosis: LayoutDiagnosis;
|
|
54
|
+
detail?: readonly string[];
|
|
55
|
+
}
|
|
56
|
+
/**
|
|
57
|
+
* The consumer-facing failure text: a site-specific headline, then the branch that matches what is
|
|
58
|
+
* on disk, then the layout dump, then the bypass. The command to run always comes before the dump,
|
|
59
|
+
* because a consumer who reads only the first screen still has to be told about `migrate`.
|
|
60
|
+
* @example
|
|
61
|
+
* formatLayoutGuidance({ headline: 'no `insider.lint.*` module found in /repo.', diagnosis });
|
|
62
|
+
*/
|
|
63
|
+
export declare function formatLayoutGuidance(input: LayoutGuidanceInput): string;
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
import { type LayoutDiagnosis } from './layoutDiagnosis';
|
|
2
|
+
export type LintHost = 'eslint' | 'oxlint' | 'unknown';
|
|
3
|
+
/**
|
|
4
|
+
* Which linter is hosting the current process. oxlint evaluates `oxlint.config.ts` inside the Node
|
|
5
|
+
* process that runs its own `bin/oxlint` wrapper, so `useInsider()` genuinely executes under both
|
|
6
|
+
* binaries and the two have to be told apart before anything is written to stdout.
|
|
7
|
+
* @example
|
|
8
|
+
* detectLintHost(['node', '/app/node_modules/oxlint/bin/oxlint', '.']); // 'oxlint'
|
|
9
|
+
*/
|
|
10
|
+
export declare function detectLintHost(argv?: readonly string[]): LintHost;
|
|
11
|
+
export type OfferSkipReason = 'already-offered' | 'cli-not-found' | 'host-is-oxlint' | 'no-tty' | 'running-in-ci' | 'running-under-test' | 'suppressed';
|
|
12
|
+
export interface MigrationOfferResult {
|
|
13
|
+
offered: boolean;
|
|
14
|
+
skipReason?: OfferSkipReason;
|
|
15
|
+
accepted?: boolean;
|
|
16
|
+
}
|
|
17
|
+
export interface MigrationOfferDeps {
|
|
18
|
+
env?: NodeJS.ProcessEnv;
|
|
19
|
+
argv?: readonly string[];
|
|
20
|
+
interactive?: boolean;
|
|
21
|
+
resolveCliEntry?: () => string | null;
|
|
22
|
+
runCli?: (entry: string, args: readonly string[], cwd: string, env: NodeJS.ProcessEnv) => number;
|
|
23
|
+
warn?: (message: string) => void;
|
|
24
|
+
}
|
|
25
|
+
/**
|
|
26
|
+
* Absolute path to this package's own built CLI, or `null` when it is not on disk. Resolved by
|
|
27
|
+
* walking up from `startDir` — this module's own directory by default — rather than through
|
|
28
|
+
* `require.resolve`, so it works from `dist/` and from `src/` alike.
|
|
29
|
+
* @example
|
|
30
|
+
* resolveCliEntry(); // '/app/node_modules/@useinsider/eslint-config/dist/cli.cjs'
|
|
31
|
+
*/
|
|
32
|
+
export declare function resolveCliEntry(startDir?: string): string | null;
|
|
33
|
+
/**
|
|
34
|
+
* Offers the guided migration for an outdated layout and runs it when the consumer accepts. Declines
|
|
35
|
+
* silently — returning a skip reason instead of prompting — whenever writing to stdout would be
|
|
36
|
+
* wrong: under oxlint, in CI, without a TTY, or when already inside a migration.
|
|
37
|
+
* @example
|
|
38
|
+
* offerMigration(diagnoseLayout('/repo')).accepted; // true after the consumer confirmed
|
|
39
|
+
*/
|
|
40
|
+
export declare function offerMigration(diagnosis: LayoutDiagnosis, deps?: MigrationOfferDeps): MigrationOfferResult;
|
|
41
|
+
/** Clears the once-per-process latch {@link offerMigration} keeps, so a suite can exercise it twice. */
|
|
42
|
+
export declare function resetMigrationOffer(): void;
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@useinsider/eslint-config",
|
|
3
3
|
"type": "module",
|
|
4
|
-
"version": "4.0.0-beta.
|
|
4
|
+
"version": "4.0.0-beta.2",
|
|
5
5
|
"description": "A collection of ESLint configurations provided by @useinsider, offering support for various environments including Vanilla JS, TypeScript, and framework-specific setups such as Vue 3.",
|
|
6
6
|
"keywords": [
|
|
7
7
|
"useinsider",
|