forked from stylelint/stylelint
/
lintSource.js
139 lines (115 loc) · 3.73 KB
/
lintSource.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
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
'use strict';
const isPathNotFoundError = require('./utils/isPathNotFoundError');
const lintPostcssResult = require('./lintPostcssResult');
const path = require('path');
/** @typedef {import('stylelint').InternalApi} StylelintInternalApi */
/** @typedef {import('stylelint').GetLintSourceOptions} Options */
/** @typedef {import('postcss').Result} Result */
/** @typedef {import('stylelint').PostcssResult} PostcssResult */
/** @typedef {import('stylelint').StylelintPostcssResult} StylelintPostcssResult */
/**
* Run stylelint on a PostCSS Result, either one that is provided
* or one that we create
* @param {StylelintInternalApi} stylelint
* @param {Options} options
* @returns {Promise<PostcssResult>}
*/
module.exports = async function lintSource(stylelint, options = {}) {
if (!options.filePath && options.code === undefined && !options.existingPostcssResult) {
return Promise.reject(new Error('You must provide filePath, code, or existingPostcssResult'));
}
const isCodeNotFile = options.code !== undefined;
const inputFilePath = isCodeNotFile ? options.codeFilename : options.filePath;
if (inputFilePath !== undefined && !path.isAbsolute(inputFilePath)) {
if (isCodeNotFile) {
return Promise.reject(new Error('codeFilename must be an absolute path'));
}
return Promise.reject(new Error('filePath must be an absolute path'));
}
const isIgnored = await stylelint.isPathIgnored(inputFilePath).catch((err) => {
if (isCodeNotFile && isPathNotFoundError(err)) return false;
throw err;
});
if (isIgnored) {
return options.existingPostcssResult
? Object.assign(options.existingPostcssResult, {
stylelint: createEmptyStylelintPostcssResult(),
})
: createEmptyPostcssResult(inputFilePath);
}
const configSearchPath = stylelint._options.configFile || inputFilePath;
const cwd = stylelint._options.cwd;
const configForFile = await stylelint
.getConfigForFile(configSearchPath, inputFilePath)
.catch((err) => {
if (isCodeNotFile && isPathNotFoundError(err)) return stylelint.getConfigForFile(cwd);
throw err;
});
if (!configForFile) {
return Promise.reject(new Error('Config file not found'));
}
const config = configForFile.config;
const existingPostcssResult = options.existingPostcssResult;
if (options.cache) {
stylelint._fileCache.calcHashOfConfig(config);
if (options.filePath && !stylelint._fileCache.hasFileChanged(options.filePath)) {
return existingPostcssResult
? Object.assign(existingPostcssResult, {
stylelint: createEmptyStylelintPostcssResult(),
})
: createEmptyPostcssResult(inputFilePath);
}
}
/** @type {StylelintPostcssResult} */
const stylelintResult = {
ruleSeverities: {},
customMessages: {},
ruleMetadata: {},
disabledRanges: {},
};
const postcssResult =
existingPostcssResult ||
(await stylelint._getPostcssResult({
code: options.code,
codeFilename: options.codeFilename,
filePath: inputFilePath,
codeProcessors: config.codeProcessors,
customSyntax: config.customSyntax,
}));
const stylelintPostcssResult = Object.assign(postcssResult, {
stylelint: stylelintResult,
});
await lintPostcssResult(stylelint._options, stylelintPostcssResult, config);
return stylelintPostcssResult;
};
/**
* @returns {StylelintPostcssResult}
*/
function createEmptyStylelintPostcssResult() {
return {
ruleSeverities: {},
customMessages: {},
ruleMetadata: {},
disabledRanges: {},
ignored: true,
stylelintError: false,
stylelintWarning: false,
};
}
/**
* @param {string} [filePath]
* @returns {PostcssResult}
*/
function createEmptyPostcssResult(filePath) {
return {
root: {
source: {
input: { file: filePath },
},
},
messages: [],
opts: undefined,
stylelint: createEmptyStylelintPostcssResult(),
warn: () => {},
};
}