简体   繁体   中英

How can I use a custom tslint rule written in TypeScript with vscode-tslint without compiling to JS?

I have a custom rule written for TSlint in TypeScript that I can run using ts-node in a script I'm using on my Linux VM:

#!/bin/bash
set -e
ROOT_DIR=$(dirname $(dirname $0))
cd $ROOT_DIR
find "$ROOT_DIR/src" -name "*.ts" -o -name "*.tsx" | xargs $(yarn bin)/ts-node $(yarn bin)/tslint

This enables tslint to run the TS rule directly without compiling first, and it does work.

The problem is that ms-vscode.vscode-typescript-tslint-plugin isn't picking up that rule even though it's explicitly enabled in the tsconfig.json rules. I am running VSCode on a separate machine with a Windows host, mounting the filesystem via Samba served from the Linux VM. Other rules in the file are being respected and shown for installed and built-in rules, like no-console , etc.

How can I get information about why the rule isn't being applied? Is there something I need to configure in the plugin to make this work?

Here's what I think might be related to the problem.

  • Let us name the rule file noImportsRule.ts . Rules are referenced in tslint.json with their kebab-cased identifier, so "no-imports": true would configure the rule.

  • Core rules cannot be overwritten with a custom implementation.

  • Custom rules can also take in options just like core rules (retrieved via this.getOptions())

  • As of TSLint v5.7.0 you no longer need to compile your custom rules before using them. You need to tell node.js how to load .ts files for example by using ts-node:

Important conventions:

  • Rule identifiers are always kebab-cased.
  • Rule files are always camel-cased ( camelCasedRule.ts ).
  • Rule files must contain the suffix Rule .
  • The exported class must always be named Rule and extend from Lint.Rules.AbstractRule

for all details

Unfortunately, this is not supported by VScode/vscode-typescript-tslint-plugin and doesn't seem to be in their agenda.

Here is a closed issue on their GitHub asking for this feature.

You can of course compile your rule to JS first, but it is not what you asked for.

The hack I develop goes like this:

  1. assume your custom rules lives under ./rules , the directory looks like:
rules/
  |- registerRule.js
  |- oneRule.ts
  |- twoRule.ts
  1. oneRule.ts and twoRule.ts are actual rules written in typescript, but registerRule.js is a "spy". The purpose of this spy rule is just to get itself picked-up by tslint instance and inject the ts-node/register into the node runtime.
// registerRule.js

require('ts-node/register')

const Lint = require('tslint')

class Rule extends Lint.Rules.AbstractRule {
  apply(sourceFile) {
    return []
  }
}

module.exports.Rule = Rule
  1. setup tslint.json
{
  "rulesDirectory": "./rules",
  "rules": {
    "register": true,
    "one": true,
    "two": true
  }
}

I've tested. This hack will teach the vscode tslint plugin to understand .ts custom rules.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM