@teambit/oxc.linter.oxlint-node 0.0.1
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/fixes.d.ts +12 -0
- package/dist/fixes.js +26 -0
- package/dist/fixes.js.map +1 -0
- package/dist/index.d.ts +2 -0
- package/dist/index.js +6 -0
- package/dist/index.js.map +1 -0
- package/dist/options.d.ts +34 -0
- package/dist/options.js +3 -0
- package/dist/options.js.map +1 -0
- package/dist/oxlint-node.d.ts +22 -0
- package/dist/oxlint-node.docs.mdx +68 -0
- package/dist/oxlint-node.js +68 -0
- package/dist/oxlint-node.js.map +1 -0
- package/dist/oxlint-node.spec.d.ts +1 -0
- package/dist/oxlint-node.spec.js +28 -0
- package/dist/oxlint-node.spec.js.map +1 -0
- package/dist/plugins.d.ts +22 -0
- package/dist/plugins.js +26 -0
- package/dist/plugins.js.map +1 -0
- package/dist/preview-1726651799114.js +7 -0
- package/dist/resolve-bin.d.ts +4 -0
- package/dist/resolve-bin.js +32 -0
- package/dist/resolve-bin.js.map +1 -0
- package/dist/rules.d.ts +14 -0
- package/dist/rules.js +18 -0
- package/dist/rules.js.map +1 -0
- package/fixes.ts +28 -0
- package/index.ts +2 -0
- package/options.ts +42 -0
- package/oxlint-node.docs.mdx +68 -0
- package/oxlint-node.spec.ts +28 -0
- package/oxlint-node.ts +86 -0
- package/package.json +44 -0
- package/plugins.ts +39 -0
- package/resolve-bin.ts +36 -0
- package/rules.ts +24 -0
- package/types/asset.d.ts +29 -0
- package/types/style.d.ts +42 -0
package/dist/fixes.d.ts
ADDED
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
export type FixesFlags = Partial<{
|
|
2
|
+
all: boolean;
|
|
3
|
+
suggestions: boolean;
|
|
4
|
+
dangerously: boolean;
|
|
5
|
+
}>;
|
|
6
|
+
export type FixType = keyof FixesFlags;
|
|
7
|
+
export declare class Fixes {
|
|
8
|
+
flags: FixesFlags;
|
|
9
|
+
constructor(flags: FixesFlags);
|
|
10
|
+
toCliArgs(): string[];
|
|
11
|
+
static from(flags: FixesFlags): Fixes;
|
|
12
|
+
}
|
package/dist/fixes.js
ADDED
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.Fixes = void 0;
|
|
4
|
+
class Fixes {
|
|
5
|
+
constructor(flags) {
|
|
6
|
+
this.flags = flags;
|
|
7
|
+
}
|
|
8
|
+
toCliArgs() {
|
|
9
|
+
return Object.keys(this.flags).reduce((acc, key) => {
|
|
10
|
+
if (this.flags[key]) {
|
|
11
|
+
if (key === 'all') {
|
|
12
|
+
acc.push('--fix');
|
|
13
|
+
}
|
|
14
|
+
else {
|
|
15
|
+
acc.push(`--fix-${key}`);
|
|
16
|
+
}
|
|
17
|
+
}
|
|
18
|
+
return acc;
|
|
19
|
+
}, []);
|
|
20
|
+
}
|
|
21
|
+
static from(flags) {
|
|
22
|
+
return new Fixes(flags);
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
exports.Fixes = Fixes;
|
|
26
|
+
//# sourceMappingURL=fixes.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"fixes.js","sourceRoot":"","sources":["../fixes.ts"],"names":[],"mappings":";;;AAQA,MAAa,KAAK;IAChB,YAAmB,KAAiB;QAAjB,UAAK,GAAL,KAAK,CAAY;IAAG,CAAC;IAExC,SAAS;QACP,OAAO,MAAM,CAAC,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,MAAM,CAAC,CAAC,GAAG,EAAE,GAAG,EAAE,EAAE;YACjD,IAAI,IAAI,CAAC,KAAK,CAAC,GAAc,CAAC,EAAE,CAAC;gBAC/B,IAAI,GAAG,KAAK,KAAK,EAAE,CAAC;oBAClB,GAAG,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;gBACpB,CAAC;qBAAM,CAAC;oBACN,GAAG,CAAC,IAAI,CAAC,SAAS,GAAG,EAAE,CAAC,CAAC;gBAC3B,CAAC;YACH,CAAC;YACD,OAAO,GAAG,CAAC;QACb,CAAC,EAAE,EAAc,CAAC,CAAC;IACrB,CAAC;IAED,MAAM,CAAC,IAAI,CAAC,KAAiB;QAC3B,OAAO,IAAI,KAAK,CAAC,KAAK,CAAC,CAAC;IAC1B,CAAC;CACF;AAnBD,sBAmBC"}
|
package/dist/index.d.ts
ADDED
package/dist/index.js
ADDED
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.OxlintNode = void 0;
|
|
4
|
+
var oxlint_node_1 = require("./oxlint-node");
|
|
5
|
+
Object.defineProperty(exports, "OxlintNode", { enumerable: true, get: function () { return oxlint_node_1.OxlintNode; } });
|
|
6
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../index.ts"],"names":[],"mappings":";;;AAAA,6CAA2C;AAAlC,yGAAA,UAAU,OAAA"}
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
import { FixesFlags } from './fixes';
|
|
2
|
+
import { PluginsFlags } from './plugins';
|
|
3
|
+
import { RulesFlags } from './rules';
|
|
4
|
+
export type OxlintFormat = 'default' | 'json' | 'unix' | 'checkstyle' | 'github';
|
|
5
|
+
export type OxlintNodeOptions = {
|
|
6
|
+
/**
|
|
7
|
+
* path to oxlint config file to use during linting
|
|
8
|
+
*/
|
|
9
|
+
configPath?: string;
|
|
10
|
+
/**
|
|
11
|
+
* path to tsconfig to use during compilation.
|
|
12
|
+
*/
|
|
13
|
+
tsconfigPath?: string;
|
|
14
|
+
/**
|
|
15
|
+
* decide the format for the CLI output.
|
|
16
|
+
*/
|
|
17
|
+
formats?: OxlintFormat[];
|
|
18
|
+
/**
|
|
19
|
+
* decide the plugins to enable.
|
|
20
|
+
*/
|
|
21
|
+
pluginsFlags?: PluginsFlags;
|
|
22
|
+
/**
|
|
23
|
+
* decide the rules / categories to enable.
|
|
24
|
+
*/
|
|
25
|
+
rulesFlags?: RulesFlags;
|
|
26
|
+
/**
|
|
27
|
+
* decide the fixes to enable.
|
|
28
|
+
*/
|
|
29
|
+
fixesFlags?: FixesFlags;
|
|
30
|
+
/**
|
|
31
|
+
* path to oxlint binary.
|
|
32
|
+
*/
|
|
33
|
+
binPath?: any;
|
|
34
|
+
};
|
package/dist/options.js
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"options.js","sourceRoot":"","sources":["../options.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
import { OxlintFormat, OxlintNodeOptions } from './options';
|
|
2
|
+
import { Plugins } from './plugins';
|
|
3
|
+
import { Rules } from './rules';
|
|
4
|
+
import { Fixes } from './fixes';
|
|
5
|
+
export type OxlintMultiFormatResult = Partial<Record<OxlintFormat, any>>;
|
|
6
|
+
export declare class OxlintNode {
|
|
7
|
+
binPath: string;
|
|
8
|
+
plugins: Plugins;
|
|
9
|
+
rules: Rules;
|
|
10
|
+
fixes: Fixes;
|
|
11
|
+
formats: OxlintFormat[];
|
|
12
|
+
configPath?: string | undefined;
|
|
13
|
+
tsconfigPath?: string | undefined;
|
|
14
|
+
constructor(binPath: string, plugins: Plugins, rules: Rules, fixes: Fixes, formats?: OxlintFormat[], configPath?: string | undefined, tsconfigPath?: string | undefined);
|
|
15
|
+
version(): Promise<string>;
|
|
16
|
+
private getConfigCliArg;
|
|
17
|
+
private getTsConfigCliArg;
|
|
18
|
+
private getFormatCliArg;
|
|
19
|
+
run(paths?: string[]): Promise<OxlintMultiFormatResult>;
|
|
20
|
+
toCliArgs(format: OxlintFormat, paths?: string[]): string[];
|
|
21
|
+
static create(options: OxlintNodeOptions): OxlintNode;
|
|
22
|
+
}
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
---
|
|
2
|
+
labels: ['Oxlint', 'module']
|
|
3
|
+
description: 'A Node.js wrapper around oxlint binary.'
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
## Installation
|
|
7
|
+
|
|
8
|
+
To install the Oxlint Node.js API, you can use `pnpm`, `npm`, or `yarn`.
|
|
9
|
+
|
|
10
|
+
### Using `pnpm`
|
|
11
|
+
|
|
12
|
+
```bash
|
|
13
|
+
pnpm add @teambit/oxc.linter.oxlint-node
|
|
14
|
+
```
|
|
15
|
+
|
|
16
|
+
### Using `npm`
|
|
17
|
+
|
|
18
|
+
```bash
|
|
19
|
+
npm install @teambit/oxc.linter.oxlint-node
|
|
20
|
+
```
|
|
21
|
+
|
|
22
|
+
### Using `yarn`
|
|
23
|
+
|
|
24
|
+
```bash
|
|
25
|
+
yarn add @teambit/oxc.linter.oxlint-node
|
|
26
|
+
```
|
|
27
|
+
|
|
28
|
+
## Usage
|
|
29
|
+
|
|
30
|
+
### Simple Usage
|
|
31
|
+
|
|
32
|
+
```javascript
|
|
33
|
+
import { OxlintNode } from '@teambit/oxc.linter.oxlint-node';
|
|
34
|
+
|
|
35
|
+
const oxlintNode = OxlintNode.create({});
|
|
36
|
+
const result = await oxlintNode.run(['paths']);
|
|
37
|
+
console.log(result);
|
|
38
|
+
```
|
|
39
|
+
|
|
40
|
+
### Advanced Usage
|
|
41
|
+
|
|
42
|
+
```javascript
|
|
43
|
+
const oxlintNode = OxlintNode.create({
|
|
44
|
+
binPath: 'path to oxlint binary',
|
|
45
|
+
formats: ['json', 'default'],
|
|
46
|
+
configPath: 'path to oxlint config file',
|
|
47
|
+
tsconfigPath: 'path to tsconfig',
|
|
48
|
+
pluginsFlags: {
|
|
49
|
+
'plugin-name': true,
|
|
50
|
+
},
|
|
51
|
+
rulesFlags: [{
|
|
52
|
+
name: 'rule-name',
|
|
53
|
+
severity: 'warn',
|
|
54
|
+
}],
|
|
55
|
+
fixesFlags: {
|
|
56
|
+
all: true,
|
|
57
|
+
}
|
|
58
|
+
});
|
|
59
|
+
```
|
|
60
|
+
|
|
61
|
+
### Other Related Components:
|
|
62
|
+
|
|
63
|
+
- **Oxlint Env Example**: [bit.cloud/teambit/oxc/examples/envs/oxlint-env](https://bit.cloud/teambit/oxc/examples/envs/oxlint-env)
|
|
64
|
+
- **Oxlint Linter**: [bit.cloud/teambit/oxc/linter/oxlint-linter](https://bit.cloud/teambit/oxc/linter/oxlint-linter)
|
|
65
|
+
|
|
66
|
+
## Contributing
|
|
67
|
+
|
|
68
|
+
We welcome contributions! Please read our [Contributing Guide](https://github.com/teambit/oxlint-node/blob/main/CONTRIBUTING.md) to get started.
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
exports.OxlintNode = void 0;
|
|
7
|
+
const execa_1 = __importDefault(require("execa"));
|
|
8
|
+
const resolve_bin_1 = require("./resolve-bin");
|
|
9
|
+
const plugins_1 = require("./plugins");
|
|
10
|
+
const rules_1 = require("./rules");
|
|
11
|
+
const fixes_1 = require("./fixes");
|
|
12
|
+
class OxlintNode {
|
|
13
|
+
constructor(binPath, plugins, rules, fixes, formats = ['default'], configPath, tsconfigPath) {
|
|
14
|
+
this.binPath = binPath;
|
|
15
|
+
this.plugins = plugins;
|
|
16
|
+
this.rules = rules;
|
|
17
|
+
this.fixes = fixes;
|
|
18
|
+
this.formats = formats;
|
|
19
|
+
this.configPath = configPath;
|
|
20
|
+
this.tsconfigPath = tsconfigPath;
|
|
21
|
+
}
|
|
22
|
+
async version() {
|
|
23
|
+
const { stdout: version } = await (0, execa_1.default)(this.binPath, ['--version']);
|
|
24
|
+
return version;
|
|
25
|
+
}
|
|
26
|
+
getConfigCliArg() {
|
|
27
|
+
return this.configPath ? `--config=${this.configPath}` : '';
|
|
28
|
+
}
|
|
29
|
+
getTsConfigCliArg() {
|
|
30
|
+
return this.configPath ? `--tsconfig=${this.configPath}` : '';
|
|
31
|
+
}
|
|
32
|
+
getFormatCliArg(format) {
|
|
33
|
+
return `--format=${format}`;
|
|
34
|
+
}
|
|
35
|
+
async run(paths = []) {
|
|
36
|
+
const result = {};
|
|
37
|
+
await Promise.all(this.formats.map(async (format) => {
|
|
38
|
+
const { stdout } = await (0, execa_1.default)(this.binPath, this.toCliArgs(format, paths));
|
|
39
|
+
result[format] = stdout;
|
|
40
|
+
if (format === 'json') {
|
|
41
|
+
result[format] = JSON.parse(stdout);
|
|
42
|
+
}
|
|
43
|
+
}));
|
|
44
|
+
return result;
|
|
45
|
+
}
|
|
46
|
+
toCliArgs(format, paths = []) {
|
|
47
|
+
const args = [
|
|
48
|
+
...this.plugins.toCliArgs(),
|
|
49
|
+
...this.rules.toCliArgs(),
|
|
50
|
+
...this.fixes.toCliArgs(),
|
|
51
|
+
this.getConfigCliArg(),
|
|
52
|
+
this.getTsConfigCliArg(),
|
|
53
|
+
this.getFormatCliArg(format),
|
|
54
|
+
...paths,
|
|
55
|
+
];
|
|
56
|
+
return args;
|
|
57
|
+
}
|
|
58
|
+
static create(options) {
|
|
59
|
+
const plugins = plugins_1.Plugins.from(options.pluginsFlags || {});
|
|
60
|
+
const rules = rules_1.Rules.from(options.rulesFlags || []);
|
|
61
|
+
const fixes = fixes_1.Fixes.from(options.fixesFlags || {});
|
|
62
|
+
const binPath = options.binPath ||
|
|
63
|
+
(0, resolve_bin_1.resolveBin)('oxlint', { executable: 'oxlint', paths: [__dirname] });
|
|
64
|
+
return new OxlintNode(binPath, plugins, rules, fixes, options.formats, options.configPath, options.tsconfigPath);
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
exports.OxlintNode = OxlintNode;
|
|
68
|
+
//# sourceMappingURL=oxlint-node.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"oxlint-node.js","sourceRoot":"","sources":["../oxlint-node.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
const oxlint_node_1 = require("./oxlint-node");
|
|
4
|
+
it('renders with the correct version', async () => {
|
|
5
|
+
const oxlintNode = oxlint_node_1.OxlintNode.create({});
|
|
6
|
+
const version = await oxlintNode.version();
|
|
7
|
+
expect(version).toContain('0.9.5');
|
|
8
|
+
});
|
|
9
|
+
describe('run', () => {
|
|
10
|
+
describe('with default options', () => {
|
|
11
|
+
let oxlintNode;
|
|
12
|
+
beforeAll(() => {
|
|
13
|
+
oxlintNode = oxlint_node_1.OxlintNode.create({});
|
|
14
|
+
});
|
|
15
|
+
it('runs oxlint successfully with no files', async () => {
|
|
16
|
+
const result = await oxlintNode.run();
|
|
17
|
+
expect(result.default).toContain('Finished');
|
|
18
|
+
expect(result.default).toContain('Found 0 warnings and 0 errors');
|
|
19
|
+
});
|
|
20
|
+
it('runs oxlint successfully on the current file', async () => {
|
|
21
|
+
const result = await oxlintNode.run([__filename]);
|
|
22
|
+
expect(result.default).toContain('Finished');
|
|
23
|
+
expect(result.default).toContain('on 1 file');
|
|
24
|
+
expect(result.default).toContain('Found 0 warnings and 0 errors');
|
|
25
|
+
});
|
|
26
|
+
});
|
|
27
|
+
});
|
|
28
|
+
//# sourceMappingURL=oxlint-node.spec.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"oxlint-node.spec.js","sourceRoot":"","sources":["../oxlint-node.spec.ts"],"names":[],"mappings":";;AAAA,+CAA2C;AAE3C,EAAE,CAAC,kCAAkC,EAAE,KAAK,IAAI,EAAE;IAChD,MAAM,UAAU,GAAG,wBAAU,CAAC,MAAM,CAAC,EAAE,CAAC,CAAC;IACzC,MAAM,OAAO,GAAG,MAAM,UAAU,CAAC,OAAO,EAAE,CAAC;IAC3C,MAAM,CAAC,OAAO,CAAC,CAAC,SAAS,CAAC,OAAO,CAAC,CAAC;AACrC,CAAC,CAAC,CAAC;AAEH,QAAQ,CAAC,KAAK,EAAE,GAAG,EAAE;IACnB,QAAQ,CAAC,sBAAsB,EAAE,GAAG,EAAE;QACpC,IAAI,UAAsB,CAAC;QAC3B,SAAS,CAAC,GAAG,EAAE;YACb,UAAU,GAAG,wBAAU,CAAC,MAAM,CAAC,EAAE,CAAC,CAAC;QACrC,CAAC,CAAC,CAAC;QACH,EAAE,CAAC,wCAAwC,EAAE,KAAK,IAAI,EAAE;YACtD,MAAM,MAAM,GAAG,MAAM,UAAU,CAAC,GAAG,EAAE,CAAC;YACtC,MAAM,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC,SAAS,CAAC,UAAU,CAAC,CAAC;YAC7C,MAAM,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC,SAAS,CAAC,+BAA+B,CAAC,CAAC;QACpE,CAAC,CAAC,CAAC;QAEH,EAAE,CAAC,8CAA8C,EAAE,KAAK,IAAI,EAAE;YAC5D,MAAM,MAAM,GAAG,MAAM,UAAU,CAAC,GAAG,CAAC,CAAC,UAAU,CAAC,CAAC,CAAC;YAClD,MAAM,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC,SAAS,CAAC,UAAU,CAAC,CAAC;YAC7C,MAAM,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC,SAAS,CAAC,WAAW,CAAC,CAAC;YAC9C,MAAM,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC,SAAS,CAAC,+BAA+B,CAAC,CAAC;QACpE,CAAC,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;AACL,CAAC,CAAC,CAAC"}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
export type PluginsFlags = Partial<{
|
|
2
|
+
react: boolean;
|
|
3
|
+
unicorn: boolean;
|
|
4
|
+
oxc: boolean;
|
|
5
|
+
typescript: boolean;
|
|
6
|
+
import: boolean;
|
|
7
|
+
jsdoc: boolean;
|
|
8
|
+
jest: boolean;
|
|
9
|
+
vitest: boolean;
|
|
10
|
+
'jsx-a11y': boolean;
|
|
11
|
+
nextjs: boolean;
|
|
12
|
+
'react-perf': boolean;
|
|
13
|
+
promise: boolean;
|
|
14
|
+
}>;
|
|
15
|
+
export type PluginsNames = keyof PluginsFlags;
|
|
16
|
+
export declare class Plugins {
|
|
17
|
+
flags: PluginsFlags;
|
|
18
|
+
pluginsEnabledByDefault: PluginsNames[];
|
|
19
|
+
constructor(flags: PluginsFlags);
|
|
20
|
+
toCliArgs(): string[];
|
|
21
|
+
static from(flags: PluginsFlags): Plugins;
|
|
22
|
+
}
|
package/dist/plugins.js
ADDED
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.Plugins = void 0;
|
|
4
|
+
class Plugins {
|
|
5
|
+
constructor(flags) {
|
|
6
|
+
this.flags = flags;
|
|
7
|
+
this.pluginsEnabledByDefault = ['react', 'unicorn', 'oxc', 'typescript'];
|
|
8
|
+
}
|
|
9
|
+
toCliArgs() {
|
|
10
|
+
return Object.keys(this.flags).reduce((acc, key) => {
|
|
11
|
+
const enabledByDefault = this.pluginsEnabledByDefault.includes(key);
|
|
12
|
+
if (this.flags[key] && !enabledByDefault) {
|
|
13
|
+
acc.push(`--${key}-plugin`);
|
|
14
|
+
}
|
|
15
|
+
if (!this.flags[key] && enabledByDefault) {
|
|
16
|
+
acc.push(`--disable-${key}-plugin`);
|
|
17
|
+
}
|
|
18
|
+
return acc;
|
|
19
|
+
}, []);
|
|
20
|
+
}
|
|
21
|
+
static from(flags) {
|
|
22
|
+
return new Plugins(flags);
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
exports.Plugins = Plugins;
|
|
26
|
+
//# sourceMappingURL=plugins.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"plugins.js","sourceRoot":"","sources":["../plugins.ts"],"names":[],"mappings":";;;AAiBA,MAAa,OAAO;IAGlB,YAAmB,KAAmB;QAAnB,UAAK,GAAL,KAAK,CAAc;QAFtC,4BAAuB,GAAmB,CAAC,OAAO,EAAE,SAAS,EAAE,KAAK,EAAE,YAAY,CAAC,CAAC;IAE3C,CAAC;IAE1C,SAAS;QACP,OAAO,MAAM,CAAC,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,MAAM,CAAC,CAAC,GAAG,EAAE,GAAG,EAAE,EAAE;YACjD,MAAM,gBAAgB,GAAG,IAAI,CAAC,uBAAuB,CAAC,QAAQ,CAAC,GAAmB,CAAC,CAAC;YACpF,IAAI,IAAI,CAAC,KAAK,CAAC,GAAmB,CAAC,IAAI,CAAC,gBAAgB,EAAE,CAAC;gBACzD,GAAG,CAAC,IAAI,CAAC,KAAK,GAAG,SAAS,CAAC,CAAC;YAC9B,CAAC;YACD,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,GAAmB,CAAC,IAAI,gBAAgB,EAAE,CAAC;gBACzD,GAAG,CAAC,IAAI,CAAC,aAAa,GAAG,SAAS,CAAC,CAAC;YACtC,CAAC;YACD,OAAO,GAAG,CAAC;QACb,CAAC,EAAE,EAAc,CAAC,CAAC;IACrB,CAAC;IAED,MAAM,CAAC,IAAI,CAAC,KAAmB;QAC7B,OAAO,IAAI,OAAO,CAAC,KAAK,CAAC,CAAC;IAC5B,CAAC;CACF;AArBD,0BAqBC"}
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
;
|
|
2
|
+
import * as overview_0 from '/Users/giladshoham/Library/Caches/Bit/capsules/root/c1c3547a2/teambit.oxc_linter_oxlint-node@0.0.1/dist/oxlint-node.docs.mdx';
|
|
3
|
+
|
|
4
|
+
export const compositions = [];
|
|
5
|
+
export const overview = [overview_0];
|
|
6
|
+
|
|
7
|
+
export const compositions_metadata = {"compositions":[]};
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
exports.resolveBin = resolveBin;
|
|
7
|
+
// TODO: move to another package / component
|
|
8
|
+
const find_root_1 = __importDefault(require("find-root"));
|
|
9
|
+
const path_1 = __importDefault(require("path"));
|
|
10
|
+
const fs_extra_1 = __importDefault(require("fs-extra"));
|
|
11
|
+
function resolveBin(moduleName, { executable = moduleName, paths = [process.cwd()], } = {}) {
|
|
12
|
+
let rootDir;
|
|
13
|
+
try {
|
|
14
|
+
const resolved = require.resolve(moduleName, { paths });
|
|
15
|
+
rootDir = (0, find_root_1.default)(resolved);
|
|
16
|
+
}
|
|
17
|
+
catch (e) {
|
|
18
|
+
const modJson = require.resolve(`${moduleName}/package.json`, { paths });
|
|
19
|
+
rootDir = path_1.default.dirname(modJson);
|
|
20
|
+
}
|
|
21
|
+
const packageJsonPath = path_1.default.join(rootDir, 'package.json');
|
|
22
|
+
const packageJson = fs_extra_1.default.readJsonSync(packageJsonPath);
|
|
23
|
+
if (!packageJson.bin) {
|
|
24
|
+
throw new Error(`no bin found in ${packageJson.name}@${packageJson.version} in path ${packageJsonPath}`);
|
|
25
|
+
}
|
|
26
|
+
const binProp = typeof packageJson.bin === 'string'
|
|
27
|
+
? packageJson.bin
|
|
28
|
+
: packageJson.bin[executable];
|
|
29
|
+
const binPath = path_1.default.join(rootDir, binProp);
|
|
30
|
+
return binPath;
|
|
31
|
+
}
|
|
32
|
+
//# sourceMappingURL=resolve-bin.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"resolve-bin.js","sourceRoot":"","sources":["../resolve-bin.ts"],"names":[],"mappings":";;;;;AAKA,gCA8BC;AAnCD,4CAA4C;AAC5C,0DAAiC;AACjC,gDAAwB;AACxB,wDAA0B;AAE1B,SAAgB,UAAU,CACxB,UAAkB,EAClB,EACE,UAAU,GAAG,UAAU,EACvB,KAAK,GAAG,CAAC,OAAO,CAAC,GAAG,EAAE,CAAC,MACsB,EAAE;IAEjD,IAAI,OAAO,CAAC;IACZ,IAAI,CAAC;QACH,MAAM,QAAQ,GAAG,OAAO,CAAC,OAAO,CAAC,UAAU,EAAE,EAAE,KAAK,EAAE,CAAC,CAAC;QACxD,OAAO,GAAG,IAAA,mBAAQ,EAAC,QAAQ,CAAC,CAAC;IAC/B,CAAC;IAAC,OAAO,CAAC,EAAE,CAAC;QACX,MAAM,OAAO,GAAG,OAAO,CAAC,OAAO,CAAC,GAAG,UAAU,eAAe,EAAE,EAAE,KAAK,EAAE,CAAC,CAAC;QACzE,OAAO,GAAG,cAAI,CAAC,OAAO,CAAC,OAAO,CAAC,CAAC;IAClC,CAAC;IACD,MAAM,eAAe,GAAG,cAAI,CAAC,IAAI,CAAC,OAAO,EAAE,cAAc,CAAC,CAAC;IAE3D,MAAM,WAAW,GAAG,kBAAE,CAAC,YAAY,CAAC,eAAe,CAAC,CAAC;IACrD,IAAI,CAAC,WAAW,CAAC,GAAG,EAAE,CAAC;QACrB,MAAM,IAAI,KAAK,CACb,mBAAmB,WAAW,CAAC,IAAI,IAAI,WAAW,CAAC,OAAO,YAAY,eAAe,EAAE,CACxF,CAAC;IACJ,CAAC;IAED,MAAM,OAAO,GACX,OAAO,WAAW,CAAC,GAAG,KAAK,QAAQ;QACjC,CAAC,CAAC,WAAW,CAAC,GAAG;QACjB,CAAC,CAAC,WAAW,CAAC,GAAG,CAAC,UAAU,CAAC,CAAC;IAClC,MAAM,OAAO,GAAG,cAAI,CAAC,IAAI,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;IAC5C,OAAO,OAAO,CAAC;AACjB,CAAC"}
|
package/dist/rules.d.ts
ADDED
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
export type Category = 'correctness' | 'suspicious' | 'pedantic' | 'style' | 'nursery' | 'restriction' | 'all';
|
|
2
|
+
export type Severity = 'allow' | 'warn' | 'deny';
|
|
3
|
+
export type Rule = string;
|
|
4
|
+
export type RuleSeverity = {
|
|
5
|
+
name: Rule | Category;
|
|
6
|
+
severity: Severity;
|
|
7
|
+
};
|
|
8
|
+
export type RulesFlags = RuleSeverity[];
|
|
9
|
+
export declare class Rules {
|
|
10
|
+
flags: RulesFlags;
|
|
11
|
+
constructor(flags: RulesFlags);
|
|
12
|
+
toCliArgs(): string[];
|
|
13
|
+
static from(flags: RulesFlags): Rules;
|
|
14
|
+
}
|
package/dist/rules.js
ADDED
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.Rules = void 0;
|
|
4
|
+
class Rules {
|
|
5
|
+
constructor(flags) {
|
|
6
|
+
this.flags = flags;
|
|
7
|
+
}
|
|
8
|
+
toCliArgs() {
|
|
9
|
+
return this.flags.map(({ name, severity }) => {
|
|
10
|
+
return (`--${severity}=${name}`);
|
|
11
|
+
});
|
|
12
|
+
}
|
|
13
|
+
static from(flags) {
|
|
14
|
+
return new Rules(flags);
|
|
15
|
+
}
|
|
16
|
+
}
|
|
17
|
+
exports.Rules = Rules;
|
|
18
|
+
//# sourceMappingURL=rules.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"rules.js","sourceRoot":"","sources":["../rules.ts"],"names":[],"mappings":";;;AAWA,MAAa,KAAK;IAChB,YAAmB,KAAiB;QAAjB,UAAK,GAAL,KAAK,CAAY;IAAG,CAAC;IAExC,SAAS;QACP,OAAO,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,EAAC,IAAI,EAAE,QAAQ,EAAC,EAAE,EAAE;YACzC,OAAM,CAAC,KAAK,QAAQ,IAAI,IAAI,EAAE,CAAC,CAAC;QAClC,CAAC,CAAC,CAAC;IACL,CAAC;IAED,MAAM,CAAC,IAAI,CAAC,KAAiB;QAC3B,OAAO,IAAI,KAAK,CAAC,KAAK,CAAC,CAAC;IAC1B,CAAC;CACF;AAZD,sBAYC"}
|
package/fixes.ts
ADDED
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
export type FixesFlags = Partial<{
|
|
2
|
+
all: boolean;
|
|
3
|
+
suggestions: boolean;
|
|
4
|
+
dangerously: boolean;
|
|
5
|
+
}>;
|
|
6
|
+
|
|
7
|
+
export type FixType = keyof FixesFlags;
|
|
8
|
+
|
|
9
|
+
export class Fixes {
|
|
10
|
+
constructor(public flags: FixesFlags) {}
|
|
11
|
+
|
|
12
|
+
toCliArgs(): string[] {
|
|
13
|
+
return Object.keys(this.flags).reduce((acc, key) => {
|
|
14
|
+
if (this.flags[key as FixType]) {
|
|
15
|
+
if (key === 'all') {
|
|
16
|
+
acc.push('--fix');
|
|
17
|
+
} else {
|
|
18
|
+
acc.push(`--fix-${key}`);
|
|
19
|
+
}
|
|
20
|
+
}
|
|
21
|
+
return acc;
|
|
22
|
+
}, [] as string[]);
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
static from(flags: FixesFlags): Fixes {
|
|
26
|
+
return new Fixes(flags);
|
|
27
|
+
}
|
|
28
|
+
}
|
package/index.ts
ADDED
package/options.ts
ADDED
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
import { FixesFlags } from './fixes';
|
|
2
|
+
import { PluginsFlags } from './plugins';
|
|
3
|
+
import { RulesFlags } from './rules';
|
|
4
|
+
|
|
5
|
+
export type OxlintFormat = 'default' | 'json' | 'unix' | 'checkstyle' | 'github';
|
|
6
|
+
|
|
7
|
+
export type OxlintNodeOptions = {
|
|
8
|
+
/**
|
|
9
|
+
* path to oxlint config file to use during linting
|
|
10
|
+
*/
|
|
11
|
+
configPath?: string;
|
|
12
|
+
|
|
13
|
+
/**
|
|
14
|
+
* path to tsconfig to use during compilation.
|
|
15
|
+
*/
|
|
16
|
+
tsconfigPath?: string;
|
|
17
|
+
|
|
18
|
+
/**
|
|
19
|
+
* decide the format for the CLI output.
|
|
20
|
+
*/
|
|
21
|
+
formats?: OxlintFormat[];
|
|
22
|
+
|
|
23
|
+
/**
|
|
24
|
+
* decide the plugins to enable.
|
|
25
|
+
*/
|
|
26
|
+
pluginsFlags?: PluginsFlags;
|
|
27
|
+
|
|
28
|
+
/**
|
|
29
|
+
* decide the rules / categories to enable.
|
|
30
|
+
*/
|
|
31
|
+
rulesFlags?: RulesFlags;
|
|
32
|
+
|
|
33
|
+
/**
|
|
34
|
+
* decide the fixes to enable.
|
|
35
|
+
*/
|
|
36
|
+
fixesFlags?: FixesFlags;
|
|
37
|
+
|
|
38
|
+
/**
|
|
39
|
+
* path to oxlint binary.
|
|
40
|
+
*/
|
|
41
|
+
binPath?: any;
|
|
42
|
+
};
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
---
|
|
2
|
+
labels: ['Oxlint', 'module']
|
|
3
|
+
description: 'A Node.js wrapper around oxlint binary.'
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
## Installation
|
|
7
|
+
|
|
8
|
+
To install the Oxlint Node.js API, you can use `pnpm`, `npm`, or `yarn`.
|
|
9
|
+
|
|
10
|
+
### Using `pnpm`
|
|
11
|
+
|
|
12
|
+
```bash
|
|
13
|
+
pnpm add @teambit/oxc.linter.oxlint-node
|
|
14
|
+
```
|
|
15
|
+
|
|
16
|
+
### Using `npm`
|
|
17
|
+
|
|
18
|
+
```bash
|
|
19
|
+
npm install @teambit/oxc.linter.oxlint-node
|
|
20
|
+
```
|
|
21
|
+
|
|
22
|
+
### Using `yarn`
|
|
23
|
+
|
|
24
|
+
```bash
|
|
25
|
+
yarn add @teambit/oxc.linter.oxlint-node
|
|
26
|
+
```
|
|
27
|
+
|
|
28
|
+
## Usage
|
|
29
|
+
|
|
30
|
+
### Simple Usage
|
|
31
|
+
|
|
32
|
+
```javascript
|
|
33
|
+
import { OxlintNode } from '@teambit/oxc.linter.oxlint-node';
|
|
34
|
+
|
|
35
|
+
const oxlintNode = OxlintNode.create({});
|
|
36
|
+
const result = await oxlintNode.run(['paths']);
|
|
37
|
+
console.log(result);
|
|
38
|
+
```
|
|
39
|
+
|
|
40
|
+
### Advanced Usage
|
|
41
|
+
|
|
42
|
+
```javascript
|
|
43
|
+
const oxlintNode = OxlintNode.create({
|
|
44
|
+
binPath: 'path to oxlint binary',
|
|
45
|
+
formats: ['json', 'default'],
|
|
46
|
+
configPath: 'path to oxlint config file',
|
|
47
|
+
tsconfigPath: 'path to tsconfig',
|
|
48
|
+
pluginsFlags: {
|
|
49
|
+
'plugin-name': true,
|
|
50
|
+
},
|
|
51
|
+
rulesFlags: [{
|
|
52
|
+
name: 'rule-name',
|
|
53
|
+
severity: 'warn',
|
|
54
|
+
}],
|
|
55
|
+
fixesFlags: {
|
|
56
|
+
all: true,
|
|
57
|
+
}
|
|
58
|
+
});
|
|
59
|
+
```
|
|
60
|
+
|
|
61
|
+
### Other Related Components:
|
|
62
|
+
|
|
63
|
+
- **Oxlint Env Example**: [bit.cloud/teambit/oxc/examples/envs/oxlint-env](https://bit.cloud/teambit/oxc/examples/envs/oxlint-env)
|
|
64
|
+
- **Oxlint Linter**: [bit.cloud/teambit/oxc/linter/oxlint-linter](https://bit.cloud/teambit/oxc/linter/oxlint-linter)
|
|
65
|
+
|
|
66
|
+
## Contributing
|
|
67
|
+
|
|
68
|
+
We welcome contributions! Please read our [Contributing Guide](https://github.com/teambit/oxlint-node/blob/main/CONTRIBUTING.md) to get started.
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
import { OxlintNode } from './oxlint-node';
|
|
2
|
+
|
|
3
|
+
it('renders with the correct version', async () => {
|
|
4
|
+
const oxlintNode = OxlintNode.create({});
|
|
5
|
+
const version = await oxlintNode.version();
|
|
6
|
+
expect(version).toContain('0.9.5');
|
|
7
|
+
});
|
|
8
|
+
|
|
9
|
+
describe('run', () => {
|
|
10
|
+
describe('with default options', () => {
|
|
11
|
+
let oxlintNode: OxlintNode;
|
|
12
|
+
beforeAll(() => {
|
|
13
|
+
oxlintNode = OxlintNode.create({});
|
|
14
|
+
});
|
|
15
|
+
it('runs oxlint successfully with no files', async () => {
|
|
16
|
+
const result = await oxlintNode.run();
|
|
17
|
+
expect(result.default).toContain('Finished');
|
|
18
|
+
expect(result.default).toContain('Found 0 warnings and 0 errors');
|
|
19
|
+
});
|
|
20
|
+
|
|
21
|
+
it('runs oxlint successfully on the current file', async () => {
|
|
22
|
+
const result = await oxlintNode.run([__filename]);
|
|
23
|
+
expect(result.default).toContain('Finished');
|
|
24
|
+
expect(result.default).toContain('on 1 file');
|
|
25
|
+
expect(result.default).toContain('Found 0 warnings and 0 errors');
|
|
26
|
+
});
|
|
27
|
+
});
|
|
28
|
+
});
|
package/oxlint-node.ts
ADDED
|
@@ -0,0 +1,86 @@
|
|
|
1
|
+
import execa from 'execa';
|
|
2
|
+
import { resolveBin } from './resolve-bin';
|
|
3
|
+
import { OxlintFormat, OxlintNodeOptions } from './options';
|
|
4
|
+
import { Plugins } from './plugins';
|
|
5
|
+
import { Rules } from './rules';
|
|
6
|
+
import { Fixes } from './fixes';
|
|
7
|
+
|
|
8
|
+
export type OxlintMultiFormatResult = Partial<Record<OxlintFormat, any>>;
|
|
9
|
+
|
|
10
|
+
export class OxlintNode {
|
|
11
|
+
constructor(
|
|
12
|
+
public binPath: string,
|
|
13
|
+
public plugins: Plugins,
|
|
14
|
+
public rules: Rules,
|
|
15
|
+
public fixes: Fixes,
|
|
16
|
+
public formats: OxlintFormat[] = ['default'],
|
|
17
|
+
public configPath?: string,
|
|
18
|
+
public tsconfigPath?: string
|
|
19
|
+
) {}
|
|
20
|
+
|
|
21
|
+
async version() {
|
|
22
|
+
const { stdout: version } = await execa(this.binPath, ['--version']);
|
|
23
|
+
return version;
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
private getConfigCliArg(): string {
|
|
27
|
+
return this.configPath ? `--config=${this.configPath}` : '';
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
private getTsConfigCliArg(): string {
|
|
31
|
+
return this.configPath ? `--tsconfig=${this.configPath}` : '';
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
private getFormatCliArg(format: OxlintFormat): string {
|
|
35
|
+
return `--format=${format}`;
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
async run(paths: string[] = []): Promise<OxlintMultiFormatResult> {
|
|
39
|
+
const result: OxlintMultiFormatResult = {};
|
|
40
|
+
await Promise.all(
|
|
41
|
+
this.formats.map(async (format) => {
|
|
42
|
+
const { stdout } = await execa(
|
|
43
|
+
this.binPath,
|
|
44
|
+
this.toCliArgs(format, paths)
|
|
45
|
+
);
|
|
46
|
+
result[format] = stdout;
|
|
47
|
+
if (format === 'json') {
|
|
48
|
+
result[format] = JSON.parse(stdout);
|
|
49
|
+
}
|
|
50
|
+
})
|
|
51
|
+
);
|
|
52
|
+
return result;
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
toCliArgs(format: OxlintFormat, paths: string[] = []): string[] {
|
|
56
|
+
const args = [
|
|
57
|
+
...this.plugins.toCliArgs(),
|
|
58
|
+
...this.rules.toCliArgs(),
|
|
59
|
+
...this.fixes.toCliArgs(),
|
|
60
|
+
this.getConfigCliArg(),
|
|
61
|
+
this.getTsConfigCliArg(),
|
|
62
|
+
this.getFormatCliArg(format),
|
|
63
|
+
...paths,
|
|
64
|
+
];
|
|
65
|
+
return args;
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
static create(options: OxlintNodeOptions): OxlintNode {
|
|
69
|
+
const plugins = Plugins.from(options.pluginsFlags || {});
|
|
70
|
+
const rules = Rules.from(options.rulesFlags || []);
|
|
71
|
+
const fixes = Fixes.from(options.fixesFlags || {});
|
|
72
|
+
const binPath =
|
|
73
|
+
options.binPath ||
|
|
74
|
+
resolveBin('oxlint', { executable: 'oxlint', paths: [__dirname] });
|
|
75
|
+
|
|
76
|
+
return new OxlintNode(
|
|
77
|
+
binPath,
|
|
78
|
+
plugins,
|
|
79
|
+
rules,
|
|
80
|
+
fixes,
|
|
81
|
+
options.formats,
|
|
82
|
+
options.configPath,
|
|
83
|
+
options.tsconfigPath
|
|
84
|
+
);
|
|
85
|
+
}
|
|
86
|
+
}
|
package/package.json
ADDED
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@teambit/oxc.linter.oxlint-node",
|
|
3
|
+
"version": "0.0.1",
|
|
4
|
+
"main": "dist/index.js",
|
|
5
|
+
"componentId": {
|
|
6
|
+
"name": "linter/oxlint-node",
|
|
7
|
+
"version": "0.0.1",
|
|
8
|
+
"scope": "teambit.oxc"
|
|
9
|
+
},
|
|
10
|
+
"dependencies": {
|
|
11
|
+
"execa": "^5",
|
|
12
|
+
"find-root": "^1.1.0",
|
|
13
|
+
"fs-extra": "^11.2.0",
|
|
14
|
+
"oxlint": "0.9.5"
|
|
15
|
+
},
|
|
16
|
+
"devDependencies": {
|
|
17
|
+
"@types/find-root": "^1.1.4",
|
|
18
|
+
"@types/fs-extra": "^11.0.4",
|
|
19
|
+
"@types/node": "^18.11.9",
|
|
20
|
+
"@types/jest": "^29.2.2",
|
|
21
|
+
"@teambit/node.node": "1.0.88"
|
|
22
|
+
},
|
|
23
|
+
"peerDependencies": {},
|
|
24
|
+
"license": "SEE LICENSE IN UNLICENSED",
|
|
25
|
+
"optionalDependencies": {},
|
|
26
|
+
"peerDependenciesMeta": {},
|
|
27
|
+
"private": false,
|
|
28
|
+
"engines": {
|
|
29
|
+
"node": ">=16.0.0"
|
|
30
|
+
},
|
|
31
|
+
"repository": {
|
|
32
|
+
"type": "git",
|
|
33
|
+
"url": "https://github.com/teambit/oxlint-node"
|
|
34
|
+
},
|
|
35
|
+
"keywords": [
|
|
36
|
+
"bit",
|
|
37
|
+
"oxc",
|
|
38
|
+
"linter",
|
|
39
|
+
"oxlint",
|
|
40
|
+
"node",
|
|
41
|
+
"typescript",
|
|
42
|
+
"javascript"
|
|
43
|
+
]
|
|
44
|
+
}
|
package/plugins.ts
ADDED
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
export type PluginsFlags = Partial<{
|
|
2
|
+
react: boolean;
|
|
3
|
+
unicorn: boolean;
|
|
4
|
+
oxc: boolean;
|
|
5
|
+
typescript: boolean;
|
|
6
|
+
import: boolean;
|
|
7
|
+
jsdoc: boolean;
|
|
8
|
+
jest: boolean;
|
|
9
|
+
vitest: boolean;
|
|
10
|
+
'jsx-a11y': boolean;
|
|
11
|
+
nextjs: boolean;
|
|
12
|
+
'react-perf': boolean;
|
|
13
|
+
promise: boolean;
|
|
14
|
+
}>;
|
|
15
|
+
|
|
16
|
+
export type PluginsNames = keyof PluginsFlags;
|
|
17
|
+
|
|
18
|
+
export class Plugins {
|
|
19
|
+
pluginsEnabledByDefault: PluginsNames[] = ['react', 'unicorn', 'oxc', 'typescript'];
|
|
20
|
+
|
|
21
|
+
constructor(public flags: PluginsFlags) {}
|
|
22
|
+
|
|
23
|
+
toCliArgs(): string[] {
|
|
24
|
+
return Object.keys(this.flags).reduce((acc, key) => {
|
|
25
|
+
const enabledByDefault = this.pluginsEnabledByDefault.includes(key as PluginsNames);
|
|
26
|
+
if (this.flags[key as PluginsNames] && !enabledByDefault) {
|
|
27
|
+
acc.push(`--${key}-plugin`);
|
|
28
|
+
}
|
|
29
|
+
if (!this.flags[key as PluginsNames] && enabledByDefault) {
|
|
30
|
+
acc.push(`--disable-${key}-plugin`);
|
|
31
|
+
}
|
|
32
|
+
return acc;
|
|
33
|
+
}, [] as string[]);
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
static from(flags: PluginsFlags): Plugins {
|
|
37
|
+
return new Plugins(flags);
|
|
38
|
+
}
|
|
39
|
+
}
|
package/resolve-bin.ts
ADDED
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
// TODO: move to another package / component
|
|
2
|
+
import findRoot from 'find-root';
|
|
3
|
+
import path from 'path';
|
|
4
|
+
import fs from 'fs-extra';
|
|
5
|
+
|
|
6
|
+
export function resolveBin(
|
|
7
|
+
moduleName: string,
|
|
8
|
+
{
|
|
9
|
+
executable = moduleName,
|
|
10
|
+
paths = [process.cwd()],
|
|
11
|
+
}: { executable?: string; paths?: string[] } = {}
|
|
12
|
+
): string {
|
|
13
|
+
let rootDir;
|
|
14
|
+
try {
|
|
15
|
+
const resolved = require.resolve(moduleName, { paths });
|
|
16
|
+
rootDir = findRoot(resolved);
|
|
17
|
+
} catch (e) {
|
|
18
|
+
const modJson = require.resolve(`${moduleName}/package.json`, { paths });
|
|
19
|
+
rootDir = path.dirname(modJson);
|
|
20
|
+
}
|
|
21
|
+
const packageJsonPath = path.join(rootDir, 'package.json');
|
|
22
|
+
|
|
23
|
+
const packageJson = fs.readJsonSync(packageJsonPath);
|
|
24
|
+
if (!packageJson.bin) {
|
|
25
|
+
throw new Error(
|
|
26
|
+
`no bin found in ${packageJson.name}@${packageJson.version} in path ${packageJsonPath}`
|
|
27
|
+
);
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
const binProp =
|
|
31
|
+
typeof packageJson.bin === 'string'
|
|
32
|
+
? packageJson.bin
|
|
33
|
+
: packageJson.bin[executable];
|
|
34
|
+
const binPath = path.join(rootDir, binProp);
|
|
35
|
+
return binPath;
|
|
36
|
+
}
|
package/rules.ts
ADDED
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
export type Category = 'correctness'|'suspicious'|'pedantic'|'style'|'nursery'|'restriction'|'all';
|
|
2
|
+
export type Severity = 'allow'|'warn'|'deny';
|
|
3
|
+
// TODO: add specific rules
|
|
4
|
+
export type Rule = string;
|
|
5
|
+
|
|
6
|
+
export type RuleSeverity = {
|
|
7
|
+
name: Rule | Category;
|
|
8
|
+
severity: Severity;
|
|
9
|
+
}
|
|
10
|
+
export type RulesFlags = RuleSeverity[];
|
|
11
|
+
|
|
12
|
+
export class Rules {
|
|
13
|
+
constructor(public flags: RulesFlags) {}
|
|
14
|
+
|
|
15
|
+
toCliArgs(): string[] {
|
|
16
|
+
return this.flags.map(({name, severity}) => {
|
|
17
|
+
return(`--${severity}=${name}`);
|
|
18
|
+
});
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
static from(flags: RulesFlags): Rules {
|
|
22
|
+
return new Rules(flags);
|
|
23
|
+
}
|
|
24
|
+
}
|
package/types/asset.d.ts
ADDED
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
declare module '*.png' {
|
|
2
|
+
const value: any;
|
|
3
|
+
export = value;
|
|
4
|
+
}
|
|
5
|
+
declare module '*.svg' {
|
|
6
|
+
import type { FunctionComponent, SVGProps } from 'react';
|
|
7
|
+
|
|
8
|
+
export const ReactComponent: FunctionComponent<
|
|
9
|
+
SVGProps<SVGSVGElement> & { title?: string }
|
|
10
|
+
>;
|
|
11
|
+
const src: string;
|
|
12
|
+
export default src;
|
|
13
|
+
}
|
|
14
|
+
declare module '*.jpg' {
|
|
15
|
+
const value: any;
|
|
16
|
+
export = value;
|
|
17
|
+
}
|
|
18
|
+
declare module '*.jpeg' {
|
|
19
|
+
const value: any;
|
|
20
|
+
export = value;
|
|
21
|
+
}
|
|
22
|
+
declare module '*.gif' {
|
|
23
|
+
const value: any;
|
|
24
|
+
export = value;
|
|
25
|
+
}
|
|
26
|
+
declare module '*.bmp' {
|
|
27
|
+
const value: any;
|
|
28
|
+
export = value;
|
|
29
|
+
}
|
package/types/style.d.ts
ADDED
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
declare module '*.module.css' {
|
|
2
|
+
const classes: { readonly [key: string]: string };
|
|
3
|
+
export default classes;
|
|
4
|
+
}
|
|
5
|
+
declare module '*.module.scss' {
|
|
6
|
+
const classes: { readonly [key: string]: string };
|
|
7
|
+
export default classes;
|
|
8
|
+
}
|
|
9
|
+
declare module '*.module.sass' {
|
|
10
|
+
const classes: { readonly [key: string]: string };
|
|
11
|
+
export default classes;
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
declare module '*.module.less' {
|
|
15
|
+
const classes: { readonly [key: string]: string };
|
|
16
|
+
export default classes;
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
declare module '*.less' {
|
|
20
|
+
const classes: { readonly [key: string]: string };
|
|
21
|
+
export default classes;
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
declare module '*.css' {
|
|
25
|
+
const classes: { readonly [key: string]: string };
|
|
26
|
+
export default classes;
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
declare module '*.sass' {
|
|
30
|
+
const classes: { readonly [key: string]: string };
|
|
31
|
+
export default classes;
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
declare module '*.scss' {
|
|
35
|
+
const classes: { readonly [key: string]: string };
|
|
36
|
+
export default classes;
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
declare module '*.mdx' {
|
|
40
|
+
const component: any;
|
|
41
|
+
export default component;
|
|
42
|
+
}
|