ESLint - Only Allow Relative Import Paths Not Absolute - node.js

On a similar note as the question ESLint - Only Allow Absolute Import Paths Not Relative
How can eslint made to error on absolute imports? Specifically interested in the context of TypeScript.

You could try to use the rule #typescript-eslint/no-restricted-imports to disallow absolute imports (anything that does not start with ./ or ../).
{
rules: {
"no-restricted-imports": "off",
"#typescript-eslint/no-restricted-imports": [
"error",
{
"patterns": ["!./*", "!../*"]
}
]
}
}
#typescript-eslint/no-restricted-imports extends eslint/no-restricted-imports.
The reason why we disable eslint/no-restricted-imports is because it can report incorrect errors.
More information here.

set 'relative path only' in IDE and remove baseUrl from tsconfig.json

Related

Import module with absolute path using jsconfig.json not working in Node JS

It is difficult to refer the modules using relative path in the project. To achieve this we tried to using jsconfig.json on the client (react) project to refer from the absolute path. Below is my jsconfig.json file. It is working fine.
{
"compilerOptions": {
"baseUrl": "./src"
}
}
I am not able to achieve the same on server ( node js ) project. Getting the error messages
cannot find module
Any reference would be appreciated.
You can use baseUrl along with paths to fix the errors.
Paths allow us to aggregate a list directories under a predefined name and drastically reduce the length of the imports.
Here is a template on how to setup them your jsconfig.json.
jsconfig.json
{
"compilerOptions": {
"baseUrl": ".",
"paths": {
"#routes/*": [
"./routes/*"
],
"#models/*": [
"./models/*"
],
"#datetime/*": [
"./utils/datetime/*"
]
}
}
}
We are aggregating all the files in the models folder under the name #models. The same is the case for routes and datetime. We would be able to reference the folders using #routes, #models, and #datetime in the import statement.
So, after you've setup your jsconfig, you need to change the relative paths to absolute paths. For example:
server.js
// Before jsconfig
import adminRoutes from "../../src/routes/admin"
// After jsconfig
import adminRoutes from "#routes/admin"
I hope it helps!
Read the source for more details.

ESLint disable default export

So far I've been unable to figure out a ready to use solution for throwing an error if something does a default export.
We internally have the standard to only do named exports, but I'd like the linter to ensure it doesn't happen.
Is there a way to accomplish this short of writing a custom rule?
EDIT: I'm assuming, but could very easily be wrong, that I could use the no-restricted-syntax rule like I was pointed to here. I just didn't want to reach for that if there was a better solution.
It would be best to use eslint-plugin-import to enforce import and export rules. It has a lovely rule to prevent default exports import/no-default-export.
npm install --save-dev eslint-plugin-import
.eslintrc
{
"plugins": [
"import"
],
"rules": {
"import/no-default-export": "error"
}
}

eslint rule #nrwl/nx/enforce-module-boundaries fails

Intro
I was very confused with that rule when I recently ported the Ng code base to Nx 12.x. I hope this post helps others who begin migrating from Ng to Nx.
The code base above is a rather small single repo which is now used in production. When using Nx it's a good practice to follow the recommendations for monorepo to be able to use the monorepo benefits in the future as the code base is growing. (E.g. here I'm avoiding the overexposing of the code in the current repo).
I put the code base above into my-org/apps/my-small-repo. By linting I was confused by the failure of the rule #nrwl/nx/enforce-module-boundaries. So I tried different possibilities of mapping the src/app of my-org/apps/my-small-repo where either compiler or linter or both just failed.
I figured out the following solutions.
Solution 1
Just put
"compilerOptions": {
"baseUrl": "src"
},
into the root of apps/my-small-repo/tsconfig.json and replace all of your imports inside of apps/my-small-repo with imports beginning with app.
Example for a DashboardComponent:
import { DashboardComponent } from 'app/components/dashboard/dashboard.component';
Probably a better solution
This solution is tested on nx 13.x, but it probably works on previous versions of nx also.
Put
"app/*": ["apps/my-org/src/app/*"]
to the paths in compilerOptions of your tsconfig.base.json in the repo root. Then put "allowCircularSelfDependency": true, to the rule #nrwl/nx/enforce-module-boundaries in the repo root.
We decided for "allowCircularSelfDependency": true, to avoid working with ugly relative paths like like e.g. this one ../../../../../ in the app. And we also want to have library namespaces in tsconfig.base.json only.
Documentation of the rule
https://github.com/nrwl/nx/blob/master/packages/eslint-plugin-nx/src/rules/enforce-module-boundaries.ts
For those who are coming here without this getting resolved. (nx monorepo usage)
Trouble shooting the 2 errors (TS error and lint error):
First the Alias error:
Cannot find module '#account/components/something' or its corresponding type declarations.
On your base tsconfig.base.json (not tsconfig.json under your apps as it gets overrided), add:
"compilerOptions":{
...
baseUrl:"." // Try "src" as well incase of boiler plates or if your resolved path (on the error) is missing an src.
path: {
"#account/*": ["app/*"],
"#account/components/*": ["app/components/*"]
}
},
The above will resolve:
import { authMiddleware } from '#account/components/something';
from
import { authMiddleware } from '../../../components/something';
For lint error:
Projects should use relative imports to import from other files within the same project - eslint rule #nrwl/nx/enforce-module-boundaries fails`
Add "allowCircularSelfDependency": true.
"#nrwl/nx/enforce-module-boundaries": [
"error",
{
"allowCircularSelfDependency": true, -> This may solve the lint error.
"allow": ["#account/**"], -> // White list the lint error.
...
}
Whitelist the folders: Add "allow": [#foldername]
"#nrwl/nx/enforce-module-boundaries": [
"error",
{
"allow": ["#account/**"], -> // White list the lint error.
...
}
That should fix it.
To get this working:
On your base tsconfig.base.json or your local tsconfig.json.
I suggest to do it on the tsconfig.base.json
Considering your path apps/my-org/src/app/*
"compilerOptions":{
...
baseUrl:"src"
path: {
"#app/*": ["app/*"] // << Here is the change
}
},
Import in your code files from this apps/my-org/src/app/*
to this #app/*

ESLint Vue plugin showing false positives for vue/comment-directive

After migrating from VueCLI to Vite, I have to do the linting "manually" as far as I understand; correct me if I'm wrong.
As I only want to lint my .ts and .html files (I separate them even for components), I have this script in my package json:
"lint": "eslint --ext .ts --ext .html src/"
It found some issues like missing :key in loops, but it also shows me this error for each template:
error clear vue/comment-directive
And this is always the closing tag of any root elements within my template.html
If there is only one root element I get one warning for the file, if there are multiple root elements I get a warning for each closing tag.
I don't understand what this rule complains as, according its documentation, it is there for the eslint-disable comments, which I don't have in my templates.
I had the same issue but in nuxt with eslint, i just needed to update eslint-config and eslint-module:
"#nuxtjs/eslint-config": "^5.0.0",
"#nuxtjs/eslint-module": "^3.0.1",
source: https://github.com/nuxt/eslint-plugin-nuxt/issues/121
I've just updated my npm dependencies and I have the same error.
I was reading the eslint documentation and finally I've realized that you can remove the false error if you setup the rule in the .eslintrc.js config file.
this is my .eslintrc.js config file:
module.exports = {
root: true,
env: {
browser: true,
node: true
},
parserOptions: {
parser: 'babel-eslint'
},
extends: [
'#nuxtjs',
'prettier',
'prettier/vue',
'plugin:prettier/recommended',
'plugin:nuxt/recommended'
],
plugins: [
'prettier'
],
// add your custom rules here
rules: {
"vue/comment-directive": 0
}
}
add the rule "vue/comment-directive": 0 and that is!, the error message is removed!.
the possible values are:
0 means disabled
1 means warning
2 means error
Try to change it in your IDE to how it works
(In my case I've had to stop the server and re-run it every time that I've changed a value in this config file.)
I have the same error.
I was taught how to fix this error.
https://qiita.com/tashinoso/items/a72741ca8e2fd928ca77#comment-3e6cd674353056ecbb3a
module.exports = {
...
overrides: [
{
files: ["*.vue"],
processor: "vue/.vue"
}
]
}
Set this snippet on .eslintrc.js
"vue/comment-directive": ["error", {
"reportUnusedDisableDirectives": false
}]
Solve my issue, i wonder why. Solution from documentation
Node v12.20.0
This is a kind of a temporary fix that worked for me and I think it will work for you as well.
vue/comment-directive
This rule is included in all of "plugin:vue/base", "plugin:vue/essential", "plugin:vue/vue3-essential", "plugin:vue/strongly-recommended", "plugin:vue/vue3-strongly-recommended", "plugin:vue/recommended" and "plugin:vue/vue3-recommended".
ESLint doesn't provide any API to enhance eslint-disable functionality and ESLint rules cannot affect other rules. But ESLint provides processors API.
This rule sends all eslint-disable-like comments as errors to the post-process of the .vue file processor, then the post-process removes all vue/comment-directive errors and the reported errors in disabled areas.
All you need to do is add
eslint-disable-next-line vue/component-tags-order
this line as comment above anywhere you using comments within tags in each block you need to specify if comments are added.
For more information please visit:- https://eslint.vuejs.org/rules/comment-directive.html

ESLint - "window" is not defined. How to allow global variables in package.json

I am assigning a property to the global window object, but when I run eslint, I get this:
"window" is not defined
I see this here in the eslint docs:
the following defines window as a global variable for code that should not trigger the rule being tested:
valid: [
{
code: "window.alert()",
globals: [ "window" ]
}
]
I've tried adding something like this to the package.json file to have eslint allow "window" as a global variable, but I must be doing something wrong. From the docs it seems like I might need to do something like this in a separate file, but is there a way to define some allowed global variables right in the package.json file?
There is a builtin environment: browser that includes window.
Example .eslintrc.json:
"env": {
"browser": true,
"node": true,
"jasmine": true
},
More information: https://eslint.org/docs/user-guide/configuring/language-options#specifying-environments
Also see the package.json answer by chevin99 below.
I found it on this page: http://eslint.org/docs/user-guide/configuring
In package.json, this works:
"eslintConfig": {
"globals": {
"window": true
}
}
Add .eslintrc in the project root.
{
"globals": {
"document": true,
"foo": true,
"window": true
}
}
Your .eslintrc.json should contain the text below.
This way ESLint knows about your global variables.
{
"env": {
"browser": true,
"node": true
}
}
I'm aware he's not asking for the inline version. But since this question has almost 100k visits and I fell here looking for that, I'll leave it here for the next fellow coder:
Make sure ESLint is not run with the --no-inline-config flag (if this doesn't sound familiar, you're likely good to go). Then, write this in your code file (for clarity and convention, it's written on top of the file but it'll work anywhere):
/* eslint-env browser */
This tells ESLint that your working environment is a browser, so now it knows what things are available in a browser and adapts accordingly.
There are plenty of environments, and you can declare more than one at the same time, for example, in-line:
/* eslint-env browser, node */
If you are almost always using particular environments, it's best to set it in your ESLint's config file and forget about it.
From their docs:
An environment defines global variables that are predefined. The
available environments are:
browser - browser global variables.
node - Node.js global variables and Node.js scoping.
commonjs - CommonJS global variables and CommonJS scoping (use this for browser-only code that uses Browserify/WebPack).
shared-node-browser - Globals common to both Node and Browser.
[...]
Besides environments, you can make it ignore anything you want. If it warns you about using console.log() but you don't want to be warned about it, just inline:
/* eslint-disable no-console */
You can see the list of all rules, including recommended rules to have for best coding practices.
If you are using Angular you can get it off with:
"env": {
"browser": true,
"node": true
},
"rules" : {
"angular/window-service": 0
}

Resources