Actualizacion maquina principal
[dotfiles/.git] / .config / coc / extensions / node_modules / coc-prettier / node_modules / eslint / lib / rules / spaced-comment.js
diff --git a/.config/coc/extensions/node_modules/coc-prettier/node_modules/eslint/lib/rules/spaced-comment.js b/.config/coc/extensions/node_modules/coc-prettier/node_modules/eslint/lib/rules/spaced-comment.js
new file mode 100644 (file)
index 0000000..daf56cd
--- /dev/null
@@ -0,0 +1,373 @@
+/**
+ * @fileoverview Source code for spaced-comments rule
+ * @author Gyandeep Singh
+ */
+"use strict";
+
+const lodash = require("lodash");
+const astUtils = require("./utils/ast-utils");
+
+//------------------------------------------------------------------------------
+// Helpers
+//------------------------------------------------------------------------------
+
+/**
+ * Escapes the control characters of a given string.
+ * @param {string} s A string to escape.
+ * @returns {string} An escaped string.
+ */
+function escape(s) {
+    return `(?:${lodash.escapeRegExp(s)})`;
+}
+
+/**
+ * Escapes the control characters of a given string.
+ * And adds a repeat flag.
+ * @param {string} s A string to escape.
+ * @returns {string} An escaped string.
+ */
+function escapeAndRepeat(s) {
+    return `${escape(s)}+`;
+}
+
+/**
+ * Parses `markers` option.
+ * If markers don't include `"*"`, this adds `"*"` to allow JSDoc comments.
+ * @param {string[]} [markers] A marker list.
+ * @returns {string[]} A marker list.
+ */
+function parseMarkersOption(markers) {
+
+    // `*` is a marker for JSDoc comments.
+    if (markers.indexOf("*") === -1) {
+        return markers.concat("*");
+    }
+
+    return markers;
+}
+
+/**
+ * Creates string pattern for exceptions.
+ * Generated pattern:
+ *
+ * 1. A space or an exception pattern sequence.
+ * @param {string[]} exceptions An exception pattern list.
+ * @returns {string} A regular expression string for exceptions.
+ */
+function createExceptionsPattern(exceptions) {
+    let pattern = "";
+
+    /*
+     * A space or an exception pattern sequence.
+     * []                 ==> "\s"
+     * ["-"]              ==> "(?:\s|\-+$)"
+     * ["-", "="]         ==> "(?:\s|(?:\-+|=+)$)"
+     * ["-", "=", "--=="] ==> "(?:\s|(?:\-+|=+|(?:\-\-==)+)$)" ==> https://jex.im/regulex/#!embed=false&flags=&re=(%3F%3A%5Cs%7C(%3F%3A%5C-%2B%7C%3D%2B%7C(%3F%3A%5C-%5C-%3D%3D)%2B)%24)
+     */
+    if (exceptions.length === 0) {
+
+        // a space.
+        pattern += "\\s";
+    } else {
+
+        // a space or...
+        pattern += "(?:\\s|";
+
+        if (exceptions.length === 1) {
+
+            // a sequence of the exception pattern.
+            pattern += escapeAndRepeat(exceptions[0]);
+        } else {
+
+            // a sequence of one of the exception patterns.
+            pattern += "(?:";
+            pattern += exceptions.map(escapeAndRepeat).join("|");
+            pattern += ")";
+        }
+        pattern += `(?:$|[${Array.from(astUtils.LINEBREAKS).join("")}]))`;
+    }
+
+    return pattern;
+}
+
+/**
+ * Creates RegExp object for `always` mode.
+ * Generated pattern for beginning of comment:
+ *
+ * 1. First, a marker or nothing.
+ * 2. Next, a space or an exception pattern sequence.
+ * @param {string[]} markers A marker list.
+ * @param {string[]} exceptions An exception pattern list.
+ * @returns {RegExp} A RegExp object for the beginning of a comment in `always` mode.
+ */
+function createAlwaysStylePattern(markers, exceptions) {
+    let pattern = "^";
+
+    /*
+     * A marker or nothing.
+     * ["*"]            ==> "\*?"
+     * ["*", "!"]       ==> "(?:\*|!)?"
+     * ["*", "/", "!<"] ==> "(?:\*|\/|(?:!<))?" ==> https://jex.im/regulex/#!embed=false&flags=&re=(%3F%3A%5C*%7C%5C%2F%7C(%3F%3A!%3C))%3F
+     */
+    if (markers.length === 1) {
+
+        // the marker.
+        pattern += escape(markers[0]);
+    } else {
+
+        // one of markers.
+        pattern += "(?:";
+        pattern += markers.map(escape).join("|");
+        pattern += ")";
+    }
+
+    pattern += "?"; // or nothing.
+    pattern += createExceptionsPattern(exceptions);
+
+    return new RegExp(pattern, "u");
+}
+
+/**
+ * Creates RegExp object for `never` mode.
+ * Generated pattern for beginning of comment:
+ *
+ * 1. First, a marker or nothing (captured).
+ * 2. Next, a space or a tab.
+ * @param {string[]} markers A marker list.
+ * @returns {RegExp} A RegExp object for `never` mode.
+ */
+function createNeverStylePattern(markers) {
+    const pattern = `^(${markers.map(escape).join("|")})?[ \t]+`;
+
+    return new RegExp(pattern, "u");
+}
+
+//------------------------------------------------------------------------------
+// Rule Definition
+//------------------------------------------------------------------------------
+
+module.exports = {
+    meta: {
+        type: "suggestion",
+
+        docs: {
+            description: "enforce consistent spacing after the `//` or `/*` in a comment",
+            category: "Stylistic Issues",
+            recommended: false,
+            url: "https://eslint.org/docs/rules/spaced-comment"
+        },
+
+        fixable: "whitespace",
+
+        schema: [
+            {
+                enum: ["always", "never"]
+            },
+            {
+                type: "object",
+                properties: {
+                    exceptions: {
+                        type: "array",
+                        items: {
+                            type: "string"
+                        }
+                    },
+                    markers: {
+                        type: "array",
+                        items: {
+                            type: "string"
+                        }
+                    },
+                    line: {
+                        type: "object",
+                        properties: {
+                            exceptions: {
+                                type: "array",
+                                items: {
+                                    type: "string"
+                                }
+                            },
+                            markers: {
+                                type: "array",
+                                items: {
+                                    type: "string"
+                                }
+                            }
+                        },
+                        additionalProperties: false
+                    },
+                    block: {
+                        type: "object",
+                        properties: {
+                            exceptions: {
+                                type: "array",
+                                items: {
+                                    type: "string"
+                                }
+                            },
+                            markers: {
+                                type: "array",
+                                items: {
+                                    type: "string"
+                                }
+                            },
+                            balanced: {
+                                type: "boolean",
+                                default: false
+                            }
+                        },
+                        additionalProperties: false
+                    }
+                },
+                additionalProperties: false
+            }
+        ]
+    },
+
+    create(context) {
+
+        const sourceCode = context.getSourceCode();
+
+        // Unless the first option is never, require a space
+        const requireSpace = context.options[0] !== "never";
+
+        /*
+         * Parse the second options.
+         * If markers don't include `"*"`, it's added automatically for JSDoc
+         * comments.
+         */
+        const config = context.options[1] || {};
+        const balanced = config.block && config.block.balanced;
+
+        const styleRules = ["block", "line"].reduce((rule, type) => {
+            const markers = parseMarkersOption(config[type] && config[type].markers || config.markers || []);
+            const exceptions = config[type] && config[type].exceptions || config.exceptions || [];
+            const endNeverPattern = "[ \t]+$";
+
+            // Create RegExp object for valid patterns.
+            rule[type] = {
+                beginRegex: requireSpace ? createAlwaysStylePattern(markers, exceptions) : createNeverStylePattern(markers),
+                endRegex: balanced && requireSpace ? new RegExp(`${createExceptionsPattern(exceptions)}$`, "u") : new RegExp(endNeverPattern, "u"),
+                hasExceptions: exceptions.length > 0,
+                captureMarker: new RegExp(`^(${markers.map(escape).join("|")})`, "u"),
+                markers: new Set(markers)
+            };
+
+            return rule;
+        }, {});
+
+        /**
+         * Reports a beginning spacing error with an appropriate message.
+         * @param {ASTNode} node A comment node to check.
+         * @param {string} message An error message to report.
+         * @param {Array} match An array of match results for markers.
+         * @param {string} refChar Character used for reference in the error message.
+         * @returns {void}
+         */
+        function reportBegin(node, message, match, refChar) {
+            const type = node.type.toLowerCase(),
+                commentIdentifier = type === "block" ? "/*" : "//";
+
+            context.report({
+                node,
+                fix(fixer) {
+                    const start = node.range[0];
+                    let end = start + 2;
+
+                    if (requireSpace) {
+                        if (match) {
+                            end += match[0].length;
+                        }
+                        return fixer.insertTextAfterRange([start, end], " ");
+                    }
+                    end += match[0].length;
+                    return fixer.replaceTextRange([start, end], commentIdentifier + (match[1] ? match[1] : ""));
+
+                },
+                message,
+                data: { refChar }
+            });
+        }
+
+        /**
+         * Reports an ending spacing error with an appropriate message.
+         * @param {ASTNode} node A comment node to check.
+         * @param {string} message An error message to report.
+         * @param {string} match An array of the matched whitespace characters.
+         * @returns {void}
+         */
+        function reportEnd(node, message, match) {
+            context.report({
+                node,
+                fix(fixer) {
+                    if (requireSpace) {
+                        return fixer.insertTextAfterRange([node.range[0], node.range[1] - 2], " ");
+                    }
+                    const end = node.range[1] - 2,
+                        start = end - match[0].length;
+
+                    return fixer.replaceTextRange([start, end], "");
+
+                },
+                message
+            });
+        }
+
+        /**
+         * Reports a given comment if it's invalid.
+         * @param {ASTNode} node a comment node to check.
+         * @returns {void}
+         */
+        function checkCommentForSpace(node) {
+            const type = node.type.toLowerCase(),
+                rule = styleRules[type],
+                commentIdentifier = type === "block" ? "/*" : "//";
+
+            // Ignores empty comments and comments that consist only of a marker.
+            if (node.value.length === 0 || rule.markers.has(node.value)) {
+                return;
+            }
+
+            const beginMatch = rule.beginRegex.exec(node.value);
+            const endMatch = rule.endRegex.exec(node.value);
+
+            // Checks.
+            if (requireSpace) {
+                if (!beginMatch) {
+                    const hasMarker = rule.captureMarker.exec(node.value);
+                    const marker = hasMarker ? commentIdentifier + hasMarker[0] : commentIdentifier;
+
+                    if (rule.hasExceptions) {
+                        reportBegin(node, "Expected exception block, space or tab after '{{refChar}}' in comment.", hasMarker, marker);
+                    } else {
+                        reportBegin(node, "Expected space or tab after '{{refChar}}' in comment.", hasMarker, marker);
+                    }
+                }
+
+                if (balanced && type === "block" && !endMatch) {
+                    reportEnd(node, "Expected space or tab before '*/' in comment.");
+                }
+            } else {
+                if (beginMatch) {
+                    if (!beginMatch[1]) {
+                        reportBegin(node, "Unexpected space or tab after '{{refChar}}' in comment.", beginMatch, commentIdentifier);
+                    } else {
+                        reportBegin(node, "Unexpected space or tab after marker ({{refChar}}) in comment.", beginMatch, beginMatch[1]);
+                    }
+                }
+
+                if (balanced && type === "block" && endMatch) {
+                    reportEnd(node, "Unexpected space or tab before '*/' in comment.", endMatch);
+                }
+            }
+        }
+
+        return {
+            Program() {
+                const comments = sourceCode.getAllComments();
+
+                comments.filter(token => token.type !== "Shebang").forEach(checkCommentForSpace);
+            }
+        };
+    }
+};