.gitignore added
[dotfiles/.git] / .config / coc / extensions / node_modules / coc-prettier / node_modules / stylelint / lib / rules / max-empty-lines / index.js
1 "use strict";
2
3 const _ = require("lodash");
4 const optionsMatches = require("../../utils/optionsMatches");
5 const report = require("../../utils/report");
6 const ruleMessages = require("../../utils/ruleMessages");
7 const styleSearch = require("style-search");
8 const validateOptions = require("../../utils/validateOptions");
9
10 const ruleName = "max-empty-lines";
11
12 const messages = ruleMessages(ruleName, {
13   expected: max =>
14     `Expected no more than ${max} empty ${max === 1 ? "line" : "lines"}`
15 });
16
17 const rule = function(max, options) {
18   const maxAdjacentNewlines = max + 1;
19
20   return (root, result) => {
21     const validOptions = validateOptions(
22       result,
23       ruleName,
24       {
25         actual: max,
26         possible: _.isNumber
27       },
28       {
29         actual: options,
30         possible: {
31           ignore: ["comments"]
32         },
33         optional: true
34       }
35     );
36     if (!validOptions) {
37       return;
38     }
39
40     const rootString = root.toString();
41     const repeatLFNewLines = _.repeat("\n", maxAdjacentNewlines);
42     const repeatCRLFNewLines = _.repeat("\r\n", maxAdjacentNewlines);
43     const ignoreComments = optionsMatches(options, "ignore", "comments");
44
45     styleSearch({ source: rootString, target: "\n" }, match => {
46       checkMatch(rootString, match.endIndex, root);
47     });
48
49     // We must check comments separately in order to accommodate stupid
50     // `//`-comments from SCSS, which postcss-scss converts to `/* ... */`,
51     // which adds to extra characters at the end, which messes up our
52     // warning position
53     if (!ignoreComments) {
54       root.walkComments(comment => {
55         const source =
56           (comment.raws.left || "") + comment.text + (comment.raws.right || "");
57         styleSearch({ source, target: "\n" }, match => {
58           checkMatch(source, match.endIndex, comment, 2);
59         });
60       });
61     }
62
63     function checkMatch(source, matchEndIndex, node) {
64       const offset =
65         arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : 0;
66
67       let violationIndex = false;
68       if (
69         source.substr(matchEndIndex, maxAdjacentNewlines) === repeatLFNewLines
70       ) {
71         violationIndex = matchEndIndex + maxAdjacentNewlines;
72       } else if (
73         source.substr(matchEndIndex, maxAdjacentNewlines * 2) ===
74         repeatCRLFNewLines
75       ) {
76         violationIndex = matchEndIndex + maxAdjacentNewlines * 2;
77       }
78
79       if (!violationIndex) {
80         return;
81       }
82
83       report({
84         message: messages.expected(max),
85         node,
86         index: violationIndex + offset,
87         result,
88         ruleName
89       });
90     }
91   };
92 };
93
94 rule.ruleName = ruleName;
95 rule.messages = messages;
96 module.exports = rule;