1
0
Fork 0

fix: usage of __dirname, lint rules and corresponding fixes

This commit is contained in:
Sean Sube 2022-02-02 08:40:56 -06:00
parent 052ca736d2
commit 3b7e48a494
14 changed files with 61 additions and 104 deletions

View File

@ -15,8 +15,7 @@
"eslint-plugin-mocha", "eslint-plugin-mocha",
"eslint-plugin-no-null", "eslint-plugin-no-null",
"eslint-plugin-sonarjs", "eslint-plugin-sonarjs",
"@typescript-eslint", "@typescript-eslint"
"@typescript-eslint/tslint"
], ],
"rules": { "rules": {
"@typescript-eslint/adjacent-overload-signatures": "error", "@typescript-eslint/adjacent-overload-signatures": "error",
@ -291,72 +290,6 @@
"sonarjs/no-redundant-jump": "error", "sonarjs/no-redundant-jump": "error",
"sonarjs/no-same-line-conditional": "error", "sonarjs/no-same-line-conditional": "error",
"sonarjs/no-useless-catch": "error", "sonarjs/no-useless-catch": "error",
"sonarjs/prefer-immediate-return": "error", "sonarjs/prefer-immediate-return": "error"
"@typescript-eslint/tslint/config": [
"error",
{
"rules": {
"ban": [
true,
{
"message": "use lodash isString",
"name": [
"util",
"isString"
]
},
{
"message": "use lodash isNil",
"name": [
"util",
"isNullOrUndefined"
]
}
],
"import-spacing": true,
"jsdoc-format": [
true,
"check-multiline-start"
],
"no-dynamic-delete": true,
"no-inferred-empty-object-type": true,
"no-reference-import": true,
"object-literal-sort-keys": true,
"one-line": [
true,
"check-catch",
"check-else",
"check-finally",
"check-open-brace",
"check-whitespace"
],
"prefer-switch": true,
"strict-type-predicates": true,
"trailing-comma": [
true,
{
"esSpecCompliant": true,
"multiline": {
"arrays": "always",
"functions": "never",
"object": "always"
},
"singleline": "never"
}
],
"whitespace": [
true,
"check-branch",
"check-decl",
"check-operator",
"check-separator",
"check-type",
"check-typecast",
"check-type-operator",
"check-rest-spread"
]
}
}
]
} }
} }

View File

@ -13,7 +13,7 @@
"es2017", "es2017",
"esnext.asynciterable" "esnext.asynciterable"
], ],
"module": "es6", "module": "esnext",
"moduleResolution": "node", "moduleResolution": "node",
"noImplicitAny": true, "noImplicitAny": true,
"noImplicitReturns": true, "noImplicitReturns": true,

View File

@ -1,6 +1,5 @@
import { createLogger } from 'bunyan'; import { createLogger } from 'bunyan';
import yargs from 'yargs'; import yargs from 'yargs';
const { showCompletionScript } = yargs;
import { loadConfig } from './config/index.js'; import { loadConfig } from './config/index.js';
import { CONFIG_ARGS_NAME, CONFIG_ARGS_PATH, MODE, parseArgs } from './config/args.js'; import { CONFIG_ARGS_NAME, CONFIG_ARGS_PATH, MODE, parseArgs } from './config/args.js';
@ -19,7 +18,7 @@ export const STATUS_MAX = 255;
export async function main(argv: Array<string>): Promise<number> { export async function main(argv: Array<string>): Promise<number> {
const { args, mode } = await parseArgs(argv.slice(ARGS_START)); const { args, mode } = await parseArgs(argv.slice(ARGS_START));
if (mode === MODE.complete) { if (mode === MODE.complete) {
showCompletionScript(); yargs(argv).showCompletionScript();
return STATUS_SUCCESS; return STATUS_SUCCESS;
} }

View File

@ -1,5 +1,4 @@
import yargs, { Options } from 'yargs'; import yargs, { Options } from 'yargs';
const { usage } = yargs;
import { RuleSelector, RuleSources } from '../rule/index.js'; import { RuleSelector, RuleSources } from '../rule/index.js';
import { VERSION_INFO } from '../version.js'; import { VERSION_INFO } from '../version.js';
@ -11,8 +10,6 @@ export enum MODE {
list = 'list', list = 'list',
} }
/* eslint-disable @typescript-eslint/no-explicit-any */
export const CONFIG_ARGS_NAME = 'config-name'; export const CONFIG_ARGS_NAME = 'config-name';
export const CONFIG_ARGS_PATH = 'config-path'; export const CONFIG_ARGS_PATH = 'config-path';
@ -23,6 +20,7 @@ const RULE_OPTION: Options = {
}; };
export interface Args { export interface Args {
/* eslint-disable-next-line @typescript-eslint/no-explicit-any */
args: any; args: any;
mode: string; mode: string;
} }
@ -50,15 +48,16 @@ export interface ParseResults {
export async function parseArgs(argv: Array<string>): Promise<ParseResults> { export async function parseArgs(argv: Array<string>): Promise<ParseResults> {
let mode: MODE = MODE.check; let mode: MODE = MODE.check;
const parser = usage('Usage: salty-dog <mode> [options]') const parser = yargs(argv).usage('Usage: salty-dog <mode> [options]')
.command({ .command({
command: ['check', '*'], command: ['check', '*'],
describe: 'validate the source documents', describe: 'validate the source documents',
handler: (argi: any) => { handler: (argi: unknown) => {
mode = MODE.check; mode = MODE.check;
}, },
}) })
.command({ .command({
/* eslint-disable-next-line @typescript-eslint/no-explicit-any */
builder: (cmd: any) => cmd.options({ builder: (cmd: any) => cmd.options({
coerce: { coerce: {
default: false, default: false,
@ -75,21 +74,21 @@ export async function parseArgs(argv: Array<string>): Promise<ParseResults> {
}), }),
command: ['fix'], command: ['fix'],
describe: 'validate the source document and insert defaults', describe: 'validate the source document and insert defaults',
handler: (argi: any) => { handler: (argi: unknown) => {
mode = MODE.fix; mode = MODE.fix;
}, },
}) })
.command({ .command({
command: ['list'], command: ['list'],
describe: 'list active rules', describe: 'list active rules',
handler: (argi: any) => { handler: (argi: unknown) => {
mode = MODE.list; mode = MODE.list;
}, },
}) })
.command({ .command({
command: ['complete'], command: ['complete'],
describe: 'generate tab completion script for bash or zsh', describe: 'generate tab completion script for bash or zsh',
handler: (argi: any) => { handler: (argi: unknown) => {
mode = MODE.complete; mode = MODE.complete;
}, },
}) })
@ -165,6 +164,7 @@ export async function parseArgs(argv: Array<string>): Promise<ParseResults> {
.alias('version', 'v'); .alias('version', 'v');
// @TODO: this should not need a cast but the parser's type omits command options and doesn't expose camelCase // @TODO: this should not need a cast but the parser's type omits command options and doesn't expose camelCase
/* eslint-disable-next-line @typescript-eslint/no-explicit-any */
const args = parser.parse(argv) as any; const args = parser.parse(argv) as any;
return { return {

View File

@ -1,7 +1,8 @@
import { doesExist, NotFoundError } from '@apextoaster/js-utils'; import { doesExist, NotFoundError } from '@apextoaster/js-utils';
import { Stream } from 'bunyan'; import { Stream } from 'bunyan';
import { LogLevel } from 'noicejs'; import { LogLevel } from 'noicejs';
import { join } from 'path'; import { dirname, join } from 'path';
import { fileURLToPath } from 'url';
import { YamlParser } from '../parser/YamlParser.js'; import { YamlParser } from '../parser/YamlParser.js';
import { readSource } from '../source.js'; import { readSource } from '../source.js';
@ -18,6 +19,10 @@ export interface ConfigData {
}; };
} }
export function dirName(): string {
return dirname(fileURLToPath(import.meta.url));
}
/** /**
* With the given name, generate all potential config paths in their complete, absolute form. * With the given name, generate all potential config paths in their complete, absolute form.
* *
@ -37,8 +42,9 @@ export function completePaths(name: string, extras: Array<string>): Array<string
paths.push(join(home, name)); paths.push(join(home, name));
} }
if (__dirname !== '') { const cwd = dirName();
paths.push(join(__dirname, name)); if (cwd !== '') {
paths.push(join(cwd, name));
} }
for (const e of extras) { for (const e of extras) {
@ -56,7 +62,9 @@ export async function loadConfig(name: string, ...extras: Array<string>): Promis
if (doesExist(data)) { if (doesExist(data)) {
const parser = new YamlParser(); const parser = new YamlParser();
const [head] = parser.parse(data); const [head] = parser.parse(data);
return head;
/* eslint-disable-next-line sonarjs/prefer-immediate-return */
return head as any; // TODO: validate config
} }
} }

View File

@ -1,5 +1,5 @@
import { VERSION_INFO } from './version.js'; import { VERSION_INFO } from './version.js';
export default { export {
VERSION_INFO, VERSION_INFO,
}; };

View File

@ -26,8 +26,8 @@ export class YamlParser implements Parser {
include.setSchema(this.schema); include.setSchema(this.schema);
} }
public dump(...data: Array<any>): string { public dump(...data: Array<unknown>): string {
const docs: Array<any> = []; const docs: Array<unknown> = [];
for (const doc of data) { for (const doc of data) {
const part = dump(doc, { const part = dump(doc, {
schema: this.schema, schema: this.schema,
@ -37,9 +37,9 @@ export class YamlParser implements Parser {
return docs.join('\n---\n\n'); return docs.join('\n---\n\n');
} }
public parse(body: string): Array<any> { public parse(body: string): Array<unknown> {
const docs: Array<any> = []; const docs: Array<unknown> = [];
loadAll(body, (doc: any) => docs.push(doc), { loadAll(body, (doc: unknown) => docs.push(doc), {
schema: this.schema, schema: this.schema,
}); });
return docs; return docs;

View File

@ -1,4 +1,4 @@
export interface Parser { export interface Parser {
dump(...data: Array<any>): string; dump(...data: Array<unknown>): string;
parse(body: string): Array<any>; parse(body: string): Array<unknown>;
} }

View File

@ -1,12 +1,12 @@
import { doesExist, hasItems } from '@apextoaster/js-utils'; import { doesExist, hasItems } from '@apextoaster/js-utils';
import { ErrorObject, ValidateFunction } from 'ajv'; import { ErrorObject, ValidateFunction } from 'ajv';
import lodash from 'lodash';
import { LogLevel } from 'noicejs'; import { LogLevel } from 'noicejs';
import { Rule, RuleData } from './index.js';
import { Visitor, VisitorError, VisitorResult } from '../visitor/index.js'; import { Visitor, VisitorError, VisitorResult } from '../visitor/index.js';
import { VisitorContext } from '../visitor/VisitorContext.js'; import { VisitorContext } from '../visitor/VisitorContext.js';
import { Rule, RuleData } from './index.js';
import lodash from 'lodash';
const { cloneDeep, defaultTo } = lodash; const { cloneDeep, defaultTo } = lodash;

View File

@ -162,13 +162,23 @@ export async function loadRulePaths(paths: Array<string>, ctx: VisitorContext):
return rules; return rules;
} }
export async function loadRuleModules(modules: Array<string>, ctx: VisitorContext, r = require): Promise<Array<Rule>> { type LoadBack = (path: string) => Promise<unknown>;
export async function loadRuleModules(modules: Array<string>, ctx: VisitorContext, load?: LoadBack): Promise<Array<Rule>> {
const rules = []; const rules = [];
function loadModule(path: string) {
if (doesExist(load)) {
return load(path);
} else {
return import(path);
}
}
for (const name of modules) { for (const name of modules) {
try { try {
/* eslint-disable-next-line @typescript-eslint/no-var-requires */ /* eslint-disable-next-line @typescript-eslint/no-var-requires */
const data: RuleSourceModule = r(name); const data: RuleSourceModule = await loadModule(name);
if (!validateRules(ctx, data)) { if (!validateRules(ctx, data)) {
ctx.logger.error({ ctx.logger.error({
module: name, module: name,
@ -218,7 +228,7 @@ export async function resolveRules(rules: Array<Rule>, selector: RuleSelector):
} }
export function validateRules(ctx: VisitorContext, root: any): boolean { export function validateRules(ctx: VisitorContext, root: any): boolean {
const { definitions, name } = {} as any; // ruleSchemaData as any; // TODO: fix this const { definitions, name } = { definitions: { config: {} } } as any; // ruleSchemaData as any;
const validCtx = new VisitorContext(ctx); const validCtx = new VisitorContext(ctx);
validCtx.addSchema(name, definitions); validCtx.addSchema(name, definitions);
@ -233,7 +243,7 @@ export function validateRules(ctx: VisitorContext, root: any): boolean {
} }
export function validateConfig(ctx: VisitorContext, root: any): boolean { export function validateConfig(ctx: VisitorContext, root: any): boolean {
const { definitions, name } = {} as any; // ruleSchemaData as any; const { definitions, name } = { definitions: { config: {} } } as any; // ruleSchemaData as any;
const validCtx = new VisitorContext(ctx); const validCtx = new VisitorContext(ctx);
validCtx.addSchema(name, definitions); validCtx.addSchema(name, definitions);

View File

@ -3,6 +3,8 @@ import { LogLevel } from 'noicejs';
import { VisitorContext } from './VisitorContext.js'; import { VisitorContext } from './VisitorContext.js';
/* eslint-disable @typescript-eslint/no-explicit-any */
/** /**
* This is a runtime error, not an exception. * This is a runtime error, not an exception.
*/ */
@ -20,7 +22,7 @@ export interface VisitorResult {
export interface Visitor<TResult extends VisitorResult = VisitorResult> { export interface Visitor<TResult extends VisitorResult = VisitorResult> {
/** /**
* Select nodes eligible to be visited. * Select nodes eligible to be visited.
**/ */
pick(ctx: VisitorContext, root: any): Promise<Array<any>>; pick(ctx: VisitorContext, root: any): Promise<Array<any>>;
/** /**

View File

@ -2,7 +2,9 @@ import { NotFoundError } from '@apextoaster/js-utils';
import { expect } from 'chai'; import { expect } from 'chai';
import { join } from 'path'; import { join } from 'path';
import { loadConfig, readConfig } from '../../src/config/index.js'; import { dirName, loadConfig, readConfig } from '../../src/config/index.js';
const __dirname = dirName();
describe('load config helper', async () => { describe('load config helper', async () => {
it('should load an existing config', async () => it('should load an existing config', async () =>

View File

@ -3,11 +3,14 @@ import { vol } from 'memfs';
import { LogLevel, NullLogger } from 'noicejs'; import { LogLevel, NullLogger } from 'noicejs';
import { spy, stub } from 'sinon'; import { spy, stub } from 'sinon';
import { dirName } from '../../src/config/index.js';
import { loadRuleFiles, loadRuleModules, loadRulePaths, loadRuleSource } from '../../src/rule/index.js'; import { loadRuleFiles, loadRuleModules, loadRulePaths, loadRuleSource } from '../../src/rule/index.js';
import { SchemaRule } from '../../src/rule/SchemaRule.js'; import { SchemaRule } from '../../src/rule/SchemaRule.js';
import { Filesystem, setFs } from '../../src/source.js'; import { Filesystem, setFs } from '../../src/source.js';
import { VisitorContext } from '../../src/visitor/VisitorContext.js'; import { VisitorContext } from '../../src/visitor/VisitorContext.js';
const __dirname = dirName();
const EXAMPLE_EMPTY = '{name: foo, definitions: {}, rules: []}'; const EXAMPLE_EMPTY = '{name: foo, definitions: {}, rules: []}';
const EXAMPLE_RULES = `{ const EXAMPLE_RULES = `{
name: foo, name: foo,

View File

@ -467,9 +467,9 @@
source-map "^0.6.0" source-map "^0.6.0"
"@types/yargs-parser@*": "@types/yargs-parser@*":
version "13.1.0" version "20.2.1"
resolved "https://artifacts.apextoaster.com/repository/group-npm/@types/yargs-parser/-/yargs-parser-13.1.0.tgz#c563aa192f39350a1d18da36c5a8da382bbd8228" resolved "https://artifacts.apextoaster.com/repository/group-npm/@types/yargs-parser/-/yargs-parser-20.2.1.tgz#3b9ce2489919d9e4fea439b76916abc34b2df129"
integrity sha512-gCubfBUZ6KxzoibJ+SCUc/57Ms1jz5NjHe4+dI2krNmU5zCPAphyLJYyTOg06ueIyfj+SaCUqmzun7ImlxDcKg== integrity sha512-7tFImggNeNBVMsn0vLrpn1H1uPrUBdnARPTpZoitY37ZrdJREzf7I16tMrlK3hen349gr1NYh8CmZQa7CTG6Aw==
"@types/yargs@17.0.8": "@types/yargs@17.0.8":
version "17.0.8" version "17.0.8"