-
Notifications
You must be signed in to change notification settings - Fork 9
/
index.js
87 lines (74 loc) · 2.12 KB
/
index.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
"use strict";
const fs = require("fs");
const path = require("path");
function has(map, path) {
let inner = map;
for (let step of path.split(".")) {
inner = inner[step];
if (inner === undefined) {
return false;
}
}
return true;
}
function findDirWithFile(filename) {
let dir = path.resolve(filename);
do {
dir = path.dirname(dir);
} while (!fs.existsSync(path.join(dir, filename)) && dir !== "/");
if (!fs.existsSync(path.join(dir, filename))) {
return;
}
return dir;
}
function getBaseUrl(baseDir) {
let url = "";
if (fs.existsSync(path.join(baseDir, "tsconfig.json"))) {
const tsconfig = JSON.parse(
fs.readFileSync(path.join(baseDir, "tsconfig.json"))
);
if (has(tsconfig, "compilerOptions.baseUrl")) {
url = tsconfig.compilerOptions.baseUrl;
}
} else if (fs.existsSync(path.join(baseDir, "jsconfig.json"))) {
const jsconfig = JSON.parse(
fs.readFileSync(path.join(baseDir, "jsconfig.json"))
);
if (has(jsconfig, "compilerOptions.baseUrl")) {
url = jsconfig.compilerOptions.baseUrl;
}
}
return path.join(baseDir, url);
}
module.exports.rules = {
"only-absolute-imports": {
meta: {
fixable: true,
},
create: function (context) {
const baseDir = findDirWithFile("package.json");
const baseUrl = getBaseUrl(baseDir);
return {
ImportDeclaration(node) {
const source = node.source.value;
if (source.startsWith(".")) {
const filename = context.getFilename();
const absolutePath = path.normalize(
path.join(path.dirname(filename), source)
);
const expectedPath = path.relative(baseUrl, absolutePath);
if (source !== expectedPath) {
context.report({
node,
message: `Relative imports are not allowed. Use \`${expectedPath}\` instead of \`${source}\`.`,
fix: function (fixer) {
return fixer.replaceText(node.source, `'${expectedPath}'`);
},
});
}
}
},
};
},
},
};