+ name = node.name.name;
+ // Exclude lowercase tag names like
+ if (isTagName(name)) {
+ return;
+ }
+ } else if (node.name.object) {
+ //
+ let parent = node.name.object;
+ while (parent.object) {
+ parent = parent.object;
+ }
+ name = parent.name;
+ } else {
+ return;
+ }
+
+ markVariableAsUsed(name, node, context);
+ },
+
+ };
+ },
+};
diff --git a/node_modules/eslint-plugin-react/lib/rules/jsx-wrap-multilines.d.ts b/node_modules/eslint-plugin-react/lib/rules/jsx-wrap-multilines.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..4b7b8013fa02f0843aa15398bb8da30734e421e8
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/jsx-wrap-multilines.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=jsx-wrap-multilines.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/jsx-wrap-multilines.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/jsx-wrap-multilines.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..abab2ad088f38cc890a9839743e1b34edd967055
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/jsx-wrap-multilines.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"jsx-wrap-multilines.d.ts","sourceRoot":"","sources":["jsx-wrap-multilines.js"],"names":[],"mappings":"wBAyCW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/jsx-wrap-multilines.js b/node_modules/eslint-plugin-react/lib/rules/jsx-wrap-multilines.js
new file mode 100644
index 0000000000000000000000000000000000000000..6f5ad50bbf5c162122a079fbd6f353ad58b776ae
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/jsx-wrap-multilines.js
@@ -0,0 +1,275 @@
+/**
+ * @fileoverview Prevent missing parentheses around multilines JSX
+ * @author Yannick Croissant
+ */
+
+'use strict';
+
+const has = require('hasown');
+const docsUrl = require('../util/docsUrl');
+const eslintUtil = require('../util/eslint');
+const jsxUtil = require('../util/jsx');
+const reportC = require('../util/report');
+const isParenthesized = require('../util/ast').isParenthesized;
+
+const getSourceCode = eslintUtil.getSourceCode;
+const getText = eslintUtil.getText;
+
+// ------------------------------------------------------------------------------
+// Constants
+// ------------------------------------------------------------------------------
+
+const DEFAULTS = {
+ declaration: 'parens',
+ assignment: 'parens',
+ return: 'parens',
+ arrow: 'parens',
+ condition: 'ignore',
+ logical: 'ignore',
+ prop: 'ignore',
+};
+
+// ------------------------------------------------------------------------------
+// Rule Definition
+// ------------------------------------------------------------------------------
+
+const messages = {
+ missingParens: 'Missing parentheses around multilines JSX',
+ extraParens: 'Expected no parentheses around multilines JSX',
+ parensOnNewLines: 'Parentheses around JSX should be on separate lines',
+};
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = {
+ meta: {
+ docs: {
+ description: 'Disallow missing parentheses around multiline JSX',
+ category: 'Stylistic Issues',
+ recommended: false,
+ url: docsUrl('jsx-wrap-multilines'),
+ },
+ fixable: 'code',
+
+ messages,
+
+ schema: [{
+ type: 'object',
+ // true/false are for backwards compatibility
+ properties: {
+ declaration: {
+ enum: [true, false, 'ignore', 'parens', 'parens-new-line', 'never'],
+ },
+ assignment: {
+ enum: [true, false, 'ignore', 'parens', 'parens-new-line', 'never'],
+ },
+ return: {
+ enum: [true, false, 'ignore', 'parens', 'parens-new-line', 'never'],
+ },
+ arrow: {
+ enum: [true, false, 'ignore', 'parens', 'parens-new-line', 'never'],
+ },
+ condition: {
+ enum: [true, false, 'ignore', 'parens', 'parens-new-line', 'never'],
+ },
+ logical: {
+ enum: [true, false, 'ignore', 'parens', 'parens-new-line', 'never'],
+ },
+ prop: {
+ enum: [true, false, 'ignore', 'parens', 'parens-new-line', 'never'],
+ },
+ },
+ additionalProperties: false,
+ }],
+ },
+
+ create(context) {
+ function getOption(type) {
+ const userOptions = context.options[0] || {};
+ if (has(userOptions, type)) {
+ return userOptions[type];
+ }
+ return DEFAULTS[type];
+ }
+
+ function isEnabled(type) {
+ const option = getOption(type);
+ return option && option !== 'ignore';
+ }
+
+ function needsOpeningNewLine(node) {
+ const previousToken = getSourceCode(context).getTokenBefore(node);
+
+ if (!isParenthesized(context, node)) {
+ return false;
+ }
+
+ if (previousToken.loc.end.line === node.loc.start.line) {
+ return true;
+ }
+
+ return false;
+ }
+
+ function needsClosingNewLine(node) {
+ const nextToken = getSourceCode(context).getTokenAfter(node);
+
+ if (!isParenthesized(context, node)) {
+ return false;
+ }
+
+ if (node.loc.end.line === nextToken.loc.end.line) {
+ return true;
+ }
+
+ return false;
+ }
+
+ function isMultilines(node) {
+ return node.loc.start.line !== node.loc.end.line;
+ }
+
+ function report(node, messageId, fix) {
+ reportC(context, messages[messageId], messageId, {
+ node,
+ fix,
+ });
+ }
+
+ function trimTokenBeforeNewline(node, tokenBefore) {
+ // if the token before the jsx is a bracket or curly brace
+ // we don't want a space between the opening parentheses and the multiline jsx
+ const isBracket = tokenBefore.value === '{' || tokenBefore.value === '[';
+ return `${tokenBefore.value.trim()}${isBracket ? '' : ' '}`;
+ }
+
+ function check(node, type) {
+ if (!node || !jsxUtil.isJSX(node)) {
+ return;
+ }
+
+ const sourceCode = getSourceCode(context);
+ const option = getOption(type);
+
+ if ((option === true || option === 'parens') && !isParenthesized(context, node) && isMultilines(node)) {
+ report(node, 'missingParens', (fixer) => fixer.replaceText(node, `(${getText(context, node)})`));
+ }
+
+ if (option === 'parens-new-line' && isMultilines(node)) {
+ if (!isParenthesized(context, node)) {
+ const tokenBefore = sourceCode.getTokenBefore(node, { includeComments: true });
+ const tokenAfter = sourceCode.getTokenAfter(node, { includeComments: true });
+ const start = node.loc.start;
+ if (tokenBefore.loc.end.line < start.line) {
+ // Strip newline after operator if parens newline is specified
+ report(
+ node,
+ 'missingParens',
+ (fixer) => fixer.replaceTextRange(
+ [tokenBefore.range[0], tokenAfter && (tokenAfter.value === ';' || tokenAfter.value === '}') ? tokenAfter.range[0] : node.range[1]],
+ `${trimTokenBeforeNewline(node, tokenBefore)}(\n${start.column > 0 ? ' '.repeat(start.column) : ''}${getText(context, node)}\n${start.column > 0 ? ' '.repeat(start.column - 2) : ''})`
+ )
+ );
+ } else {
+ report(node, 'missingParens', (fixer) => fixer.replaceText(node, `(\n${getText(context, node)}\n)`));
+ }
+ } else {
+ const needsOpening = needsOpeningNewLine(node);
+ const needsClosing = needsClosingNewLine(node);
+ if (needsOpening || needsClosing) {
+ report(node, 'parensOnNewLines', (fixer) => {
+ const text = getText(context, node);
+ let fixed = text;
+ if (needsOpening) {
+ fixed = `\n${fixed}`;
+ }
+ if (needsClosing) {
+ fixed = `${fixed}\n`;
+ }
+ return fixer.replaceText(node, fixed);
+ });
+ }
+ }
+ }
+
+ if (option === 'never' && isParenthesized(context, node)) {
+ const tokenBefore = sourceCode.getTokenBefore(node);
+ const tokenAfter = sourceCode.getTokenAfter(node);
+ report(node, 'extraParens', (fixer) => fixer.replaceTextRange(
+ [tokenBefore.range[0], tokenAfter.range[1]],
+ getText(context, node)
+ ));
+ }
+ }
+
+ // --------------------------------------------------------------------------
+ // Public
+ // --------------------------------------------------------------------------
+
+ return {
+
+ VariableDeclarator(node) {
+ const type = 'declaration';
+ if (!isEnabled(type)) {
+ return;
+ }
+ if (!isEnabled('condition') && node.init && node.init.type === 'ConditionalExpression') {
+ check(node.init.consequent, type);
+ check(node.init.alternate, type);
+ return;
+ }
+ check(node.init, type);
+ },
+
+ AssignmentExpression(node) {
+ const type = 'assignment';
+ if (!isEnabled(type)) {
+ return;
+ }
+ if (!isEnabled('condition') && node.right.type === 'ConditionalExpression') {
+ check(node.right.consequent, type);
+ check(node.right.alternate, type);
+ return;
+ }
+ check(node.right, type);
+ },
+
+ ReturnStatement(node) {
+ const type = 'return';
+ if (isEnabled(type)) {
+ check(node.argument, type);
+ }
+ },
+
+ 'ArrowFunctionExpression:exit': (node) => {
+ const arrowBody = node.body;
+ const type = 'arrow';
+
+ if (isEnabled(type) && arrowBody.type !== 'BlockStatement') {
+ check(arrowBody, type);
+ }
+ },
+
+ ConditionalExpression(node) {
+ const type = 'condition';
+ if (isEnabled(type)) {
+ check(node.consequent, type);
+ check(node.alternate, type);
+ }
+ },
+
+ LogicalExpression(node) {
+ const type = 'logical';
+ if (isEnabled(type)) {
+ check(node.right, type);
+ }
+ },
+
+ JSXAttribute(node) {
+ const type = 'prop';
+ if (isEnabled(type) && node.value && node.value.type === 'JSXExpressionContainer') {
+ check(node.value.expression, type);
+ }
+ },
+ };
+ },
+};
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-access-state-in-setstate.d.ts b/node_modules/eslint-plugin-react/lib/rules/no-access-state-in-setstate.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..68bb9eb6c0bdbc469601aa3e5ee98b161f36f6df
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-access-state-in-setstate.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=no-access-state-in-setstate.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-access-state-in-setstate.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/no-access-state-in-setstate.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..af8e61bbb7f24725856dbc0cdbf2fa5dfb9d39c9
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-access-state-in-setstate.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"no-access-state-in-setstate.d.ts","sourceRoot":"","sources":["no-access-state-in-setstate.js"],"names":[],"mappings":"wBAqBW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-access-state-in-setstate.js b/node_modules/eslint-plugin-react/lib/rules/no-access-state-in-setstate.js
new file mode 100644
index 0000000000000000000000000000000000000000..1b23dd88eee8d853ef171776e0c13e28d71e09a7
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-access-state-in-setstate.js
@@ -0,0 +1,211 @@
+/**
+ * @fileoverview Prevent usage of this.state within setState
+ * @author Rolf Erik Lekang, Jørgen Aaberg
+ */
+
+'use strict';
+
+const docsUrl = require('../util/docsUrl');
+const astUtil = require('../util/ast');
+const componentUtil = require('../util/componentUtil');
+const report = require('../util/report');
+const getScope = require('../util/eslint').getScope;
+
+// ------------------------------------------------------------------------------
+// Rule Definition
+// ------------------------------------------------------------------------------
+
+const messages = {
+ useCallback: 'Use callback in setState when referencing the previous state.',
+};
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = {
+ meta: {
+ docs: {
+ description: 'Disallow when this.state is accessed within setState',
+ category: 'Possible Errors',
+ recommended: false,
+ url: docsUrl('no-access-state-in-setstate'),
+ },
+
+ messages,
+ },
+
+ create(context) {
+ function isSetStateCall(node) {
+ return astUtil.isCallExpression(node)
+ && node.callee.property
+ && node.callee.property.name === 'setState'
+ && node.callee.object.type === 'ThisExpression';
+ }
+
+ function isFirstArgumentInSetStateCall(current, node) {
+ if (!isSetStateCall(current)) {
+ return false;
+ }
+ while (node && node.parent !== current) {
+ node = node.parent;
+ }
+ return current.arguments[0] === node;
+ }
+
+ /**
+ * @param {ASTNode} node
+ * @returns {boolean}
+ */
+ function isClassComponent(node) {
+ return !!(
+ componentUtil.getParentES6Component(context, node)
+ || componentUtil.getParentES5Component(context, node)
+ );
+ }
+
+ // The methods array contains all methods or functions that are using this.state
+ // or that are calling another method or function using this.state
+ const methods = [];
+ // The vars array contains all variables that contains this.state
+ const vars = [];
+ return {
+ CallExpression(node) {
+ if (!isClassComponent(node)) {
+ return;
+ }
+ // Appends all the methods that are calling another
+ // method containing this.state to the methods array
+ methods.forEach((method) => {
+ if ('name' in node.callee && node.callee.name === method.methodName) {
+ let current = node.parent;
+ while (current.type !== 'Program') {
+ if (current.type === 'MethodDefinition') {
+ methods.push({
+ methodName: 'name' in current.key ? current.key.name : undefined,
+ node: method.node,
+ });
+ break;
+ }
+ current = current.parent;
+ }
+ }
+ });
+
+ // Finding all CallExpressions that is inside a setState
+ // to further check if they contains this.state
+ let current = node.parent;
+ while (current.type !== 'Program') {
+ if (isFirstArgumentInSetStateCall(current, node)) {
+ const methodName = 'name' in node.callee ? node.callee.name : undefined;
+ methods.forEach((method) => {
+ if (method.methodName === methodName) {
+ report(context, messages.useCallback, 'useCallback', {
+ node: method.node,
+ });
+ }
+ });
+
+ break;
+ }
+ current = current.parent;
+ }
+ },
+
+ MemberExpression(node) {
+ if (
+ 'name' in node.property
+ && node.property.name === 'state'
+ && node.object.type === 'ThisExpression'
+ && isClassComponent(node)
+ ) {
+ /** @type {import('eslint').Rule.Node} */
+ let current = node;
+ while (current.type !== 'Program') {
+ // Reporting if this.state is directly within this.setState
+ if (isFirstArgumentInSetStateCall(current, node)) {
+ report(context, messages.useCallback, 'useCallback', {
+ node,
+ });
+ break;
+ }
+
+ // Storing all functions and methods that contains this.state
+ if (current.type === 'MethodDefinition') {
+ methods.push({
+ methodName: 'name' in current.key ? current.key.name : undefined,
+ node,
+ });
+ break;
+ } else if (
+ current.type === 'FunctionExpression'
+ && 'key' in current.parent
+ && current.parent.key
+ ) {
+ methods.push({
+ methodName: 'name' in current.parent.key ? current.parent.key.name : undefined,
+ node,
+ });
+ break;
+ }
+
+ // Storing all variables containing this.state
+ if (current.type === 'VariableDeclarator') {
+ vars.push({
+ node,
+ scope: getScope(context, node),
+ variableName: 'name' in current.id ? current.id.name : undefined,
+ });
+ break;
+ }
+
+ current = current.parent;
+ }
+ }
+ },
+
+ Identifier(node) {
+ // Checks if the identifier is a variable within an object
+ /** @type {import('eslint').Rule.Node} */
+ let current = node;
+ while (current.parent.type === 'BinaryExpression') {
+ current = current.parent;
+ }
+ if (
+ ('value' in current.parent && current.parent.value === current)
+ || ('object' in current.parent && current.parent.object === current)
+ ) {
+ while (current.type !== 'Program') {
+ if (isFirstArgumentInSetStateCall(current, node)) {
+ vars
+ .filter((v) => v.scope === getScope(context, node) && v.variableName === node.name)
+ .forEach((v) => {
+ report(context, messages.useCallback, 'useCallback', {
+ node: v.node,
+ });
+ });
+ }
+ current = current.parent;
+ }
+ }
+ },
+
+ ObjectPattern(node) {
+ const isDerivedFromThis = 'init' in node.parent && node.parent.init && node.parent.init.type === 'ThisExpression';
+ node.properties.forEach((property) => {
+ if (
+ property
+ && 'key' in property
+ && property.key
+ && 'name' in property.key
+ && property.key.name === 'state'
+ && isDerivedFromThis
+ ) {
+ vars.push({
+ node: property.key,
+ scope: getScope(context, node),
+ variableName: property.key.name,
+ });
+ }
+ });
+ },
+ };
+ },
+};
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-adjacent-inline-elements.d.ts b/node_modules/eslint-plugin-react/lib/rules/no-adjacent-inline-elements.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..50e434940a6010c3193ec0b286ccbfa6dee41e04
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-adjacent-inline-elements.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=no-adjacent-inline-elements.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-adjacent-inline-elements.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/no-adjacent-inline-elements.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..745cc94765d87334c08bfc34f6dd15740b67a29a
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-adjacent-inline-elements.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"no-adjacent-inline-elements.d.ts","sourceRoot":"","sources":["no-adjacent-inline-elements.js"],"names":[],"mappings":"wBA+EW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-adjacent-inline-elements.js b/node_modules/eslint-plugin-react/lib/rules/no-adjacent-inline-elements.js
new file mode 100644
index 0000000000000000000000000000000000000000..8110d8563b72bbeacb38ab25446b3c0fbc9644ce
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-adjacent-inline-elements.js
@@ -0,0 +1,127 @@
+/**
+ * @fileoverview Prevent adjacent inline elements not separated by whitespace.
+ * @author Sean Hayes
+ */
+
+'use strict';
+
+const docsUrl = require('../util/docsUrl');
+const isCreateElement = require('../util/isCreateElement');
+const report = require('../util/report');
+const astUtil = require('../util/ast');
+
+// ------------------------------------------------------------------------------
+// Helpers
+// ------------------------------------------------------------------------------
+
+// https://developer.mozilla.org/en-US/docs/Web/HTML/Inline_elements
+const inlineNames = [
+ 'a',
+ 'b',
+ 'big',
+ 'i',
+ 'small',
+ 'tt',
+ 'abbr',
+ 'acronym',
+ 'cite',
+ 'code',
+ 'dfn',
+ 'em',
+ 'kbd',
+ 'strong',
+ 'samp',
+ 'time',
+ 'var',
+ 'bdo',
+ 'br',
+ 'img',
+ 'map',
+ 'object',
+ 'q',
+ 'script',
+ 'span',
+ 'sub',
+ 'sup',
+ 'button',
+ 'input',
+ 'label',
+ 'select',
+ 'textarea',
+];
+// Note: raw will be transformed into \u00a0.
+const whitespaceRegex = /(?:^\s|\s$)/;
+
+function isInline(node) {
+ if (node.type === 'Literal') {
+ // Regular whitespace will be removed.
+ const value = node.value;
+ // To properly separate inline elements, each end of the literal will need
+ // whitespace.
+ return !whitespaceRegex.test(value);
+ }
+ if (node.type === 'JSXElement' && inlineNames.indexOf(node.openingElement.name.name) > -1) {
+ return true;
+ }
+ if (astUtil.isCallExpression(node) && inlineNames.indexOf(node.arguments[0].value) > -1) {
+ return true;
+ }
+ return false;
+}
+
+// ------------------------------------------------------------------------------
+// Rule Definition
+// ------------------------------------------------------------------------------
+
+const messages = {
+ inlineElement: 'Child elements which render as inline HTML elements should be separated by a space or wrapped in block level elements.',
+};
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = {
+ meta: {
+ docs: {
+ description: 'Disallow adjacent inline elements not separated by whitespace.',
+ category: 'Best Practices',
+ recommended: false,
+ url: docsUrl('no-adjacent-inline-elements'),
+ },
+ schema: [],
+
+ messages,
+ },
+ create(context) {
+ function validate(node, children) {
+ let currentIsInline = false;
+ let previousIsInline = false;
+ if (!children) {
+ return;
+ }
+ for (let i = 0; i < children.length; i++) {
+ currentIsInline = isInline(children[i]);
+ if (previousIsInline && currentIsInline) {
+ report(context, messages.inlineElement, 'inlineElement', {
+ node,
+ });
+ return;
+ }
+ previousIsInline = currentIsInline;
+ }
+ }
+ return {
+ JSXElement(node) {
+ validate(node, node.children);
+ },
+ CallExpression(node) {
+ if (!isCreateElement(context, node)) {
+ return;
+ }
+ if (node.arguments.length < 2 || !node.arguments[2]) {
+ return;
+ }
+ const children = 'elements' in node.arguments[2] ? node.arguments[2].elements : undefined;
+ validate(node, children);
+ },
+ };
+ },
+};
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-array-index-key.d.ts b/node_modules/eslint-plugin-react/lib/rules/no-array-index-key.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..7487572540920aa6bf7f486ca76d902192bc265b
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-array-index-key.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=no-array-index-key.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-array-index-key.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/no-array-index-key.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..b64273ac0146eb197e934096f16329a54d774938
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-array-index-key.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"no-array-index-key.d.ts","sourceRoot":"","sources":["no-array-index-key.js"],"names":[],"mappings":"wBA2CW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-array-index-key.js b/node_modules/eslint-plugin-react/lib/rules/no-array-index-key.js
new file mode 100644
index 0000000000000000000000000000000000000000..90381b3a08549532602dcc31af33325edd67c54c
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-array-index-key.js
@@ -0,0 +1,293 @@
+/**
+ * @fileoverview Prevent usage of Array index in keys
+ * @author Joe Lencioni
+ */
+
+'use strict';
+
+const has = require('hasown');
+const astUtil = require('../util/ast');
+const docsUrl = require('../util/docsUrl');
+const pragma = require('../util/pragma');
+const report = require('../util/report');
+const variableUtil = require('../util/variable');
+
+// ------------------------------------------------------------------------------
+// Rule Definition
+// ------------------------------------------------------------------------------
+
+function isCreateCloneElement(node, context) {
+ if (!node) {
+ return false;
+ }
+
+ if (node.type === 'MemberExpression' || node.type === 'OptionalMemberExpression') {
+ return node.object
+ && node.object.name === pragma.getFromContext(context)
+ && ['createElement', 'cloneElement'].indexOf(node.property.name) !== -1;
+ }
+
+ if (node.type === 'Identifier') {
+ const variable = variableUtil.findVariableByName(context, node, node.name);
+ if (variable && variable.type === 'ImportSpecifier') {
+ return variable.parent.source.value === 'react';
+ }
+ }
+
+ return false;
+}
+
+const messages = {
+ noArrayIndex: 'Do not use Array index in keys',
+};
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = {
+ meta: {
+ docs: {
+ description: 'Disallow usage of Array index in keys',
+ category: 'Best Practices',
+ recommended: false,
+ url: docsUrl('no-array-index-key'),
+ },
+
+ messages,
+
+ schema: [],
+ },
+
+ create(context) {
+ // --------------------------------------------------------------------------
+ // Public
+ // --------------------------------------------------------------------------
+ const indexParamNames = [];
+ const iteratorFunctionsToIndexParamPosition = {
+ every: 1,
+ filter: 1,
+ find: 1,
+ findIndex: 1,
+ flatMap: 1,
+ forEach: 1,
+ map: 1,
+ reduce: 2,
+ reduceRight: 2,
+ some: 1,
+ };
+
+ function isArrayIndex(node) {
+ return node.type === 'Identifier'
+ && indexParamNames.indexOf(node.name) !== -1;
+ }
+
+ function isUsingReactChildren(node) {
+ const callee = node.callee;
+ if (
+ !callee
+ || !callee.property
+ || !callee.object
+ ) {
+ return null;
+ }
+
+ const isReactChildMethod = ['map', 'forEach'].indexOf(callee.property.name) > -1;
+ if (!isReactChildMethod) {
+ return null;
+ }
+
+ const obj = callee.object;
+ if (obj && obj.name === 'Children') {
+ return true;
+ }
+ if (obj && obj.object && obj.object.name === pragma.getFromContext(context)) {
+ return true;
+ }
+
+ return false;
+ }
+
+ function getMapIndexParamName(node) {
+ const callee = node.callee;
+ if (callee.type !== 'MemberExpression' && callee.type !== 'OptionalMemberExpression') {
+ return null;
+ }
+ if (callee.property.type !== 'Identifier') {
+ return null;
+ }
+ if (!has(iteratorFunctionsToIndexParamPosition, callee.property.name)) {
+ return null;
+ }
+
+ const name = /** @type {keyof iteratorFunctionsToIndexParamPosition} */ (callee.property.name);
+
+ const callbackArg = isUsingReactChildren(node)
+ ? node.arguments[1]
+ : node.arguments[0];
+
+ if (!callbackArg) {
+ return null;
+ }
+
+ if (!astUtil.isFunctionLikeExpression(callbackArg)) {
+ return null;
+ }
+
+ const params = callbackArg.params;
+
+ const indexParamPosition = iteratorFunctionsToIndexParamPosition[name];
+ if (params.length < indexParamPosition + 1) {
+ return null;
+ }
+
+ return params[indexParamPosition].name;
+ }
+
+ function getIdentifiersFromBinaryExpression(side) {
+ if (side.type === 'Identifier') {
+ return side;
+ }
+
+ if (side.type === 'BinaryExpression') {
+ // recurse
+ const left = getIdentifiersFromBinaryExpression(side.left);
+ const right = getIdentifiersFromBinaryExpression(side.right);
+ return [].concat(left, right).filter(Boolean);
+ }
+
+ return null;
+ }
+
+ function checkPropValue(node) {
+ if (isArrayIndex(node)) {
+ // key={bar}
+ report(context, messages.noArrayIndex, 'noArrayIndex', {
+ node,
+ });
+ return;
+ }
+
+ if (node.type === 'TemplateLiteral') {
+ // key={`foo-${bar}`}
+ node.expressions.filter(isArrayIndex).forEach(() => {
+ report(context, messages.noArrayIndex, 'noArrayIndex', {
+ node,
+ });
+ });
+
+ return;
+ }
+
+ if (node.type === 'BinaryExpression') {
+ // key={'foo' + bar}
+ const identifiers = getIdentifiersFromBinaryExpression(node);
+
+ identifiers.filter(isArrayIndex).forEach(() => {
+ report(context, messages.noArrayIndex, 'noArrayIndex', {
+ node,
+ });
+ });
+
+ return;
+ }
+
+ if (
+ astUtil.isCallExpression(node)
+ && node.callee
+ && node.callee.type === 'MemberExpression'
+ && node.callee.object
+ && isArrayIndex(node.callee.object)
+ && node.callee.property
+ && node.callee.property.type === 'Identifier'
+ && node.callee.property.name === 'toString'
+ ) {
+ // key={bar.toString()}
+ report(context, messages.noArrayIndex, 'noArrayIndex', {
+ node,
+ });
+ return;
+ }
+
+ if (
+ astUtil.isCallExpression(node)
+ && node.callee
+ && node.callee.type === 'Identifier'
+ && node.callee.name === 'String'
+ && Array.isArray(node.arguments)
+ && node.arguments.length > 0
+ && isArrayIndex(node.arguments[0])
+ ) {
+ // key={String(bar)}
+ report(context, messages.noArrayIndex, 'noArrayIndex', {
+ node: node.arguments[0],
+ });
+ }
+ }
+
+ function popIndex(node) {
+ const mapIndexParamName = getMapIndexParamName(node);
+ if (!mapIndexParamName) {
+ return;
+ }
+
+ indexParamNames.pop();
+ }
+
+ return {
+ 'CallExpression, OptionalCallExpression'(node) {
+ if (isCreateCloneElement(node.callee, context) && node.arguments.length > 1) {
+ // React.createElement
+ if (!indexParamNames.length) {
+ return;
+ }
+
+ const props = node.arguments[1];
+
+ if (props.type !== 'ObjectExpression') {
+ return;
+ }
+
+ props.properties.forEach((prop) => {
+ if (!prop.key || prop.key.name !== 'key') {
+ // { ...foo }
+ // { foo: bar }
+ return;
+ }
+
+ checkPropValue(prop.value);
+ });
+
+ return;
+ }
+
+ const mapIndexParamName = getMapIndexParamName(node);
+ if (!mapIndexParamName) {
+ return;
+ }
+
+ indexParamNames.push(mapIndexParamName);
+ },
+
+ JSXAttribute(node) {
+ if (node.name.name !== 'key') {
+ // foo={bar}
+ return;
+ }
+
+ if (!indexParamNames.length) {
+ // Not inside a call expression that we think has an index param.
+ return;
+ }
+
+ const value = node.value;
+ if (!value || value.type !== 'JSXExpressionContainer') {
+ // key='foo' or just simply 'key'
+ return;
+ }
+
+ checkPropValue(value.expression);
+ },
+
+ 'CallExpression:exit': popIndex,
+ 'OptionalCallExpression:exit': popIndex,
+ };
+ },
+};
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-arrow-function-lifecycle.d.ts b/node_modules/eslint-plugin-react/lib/rules/no-arrow-function-lifecycle.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..f3065993062254468189f7ca3d184d173fc15588
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-arrow-function-lifecycle.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=no-arrow-function-lifecycle.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-arrow-function-lifecycle.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/no-arrow-function-lifecycle.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..707d2b3e0add90163f21995bc46933ad5bede2e5
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-arrow-function-lifecycle.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"no-arrow-function-lifecycle.d.ts","sourceRoot":"","sources":["no-arrow-function-lifecycle.js"],"names":[],"mappings":"wBAsCW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-arrow-function-lifecycle.js b/node_modules/eslint-plugin-react/lib/rules/no-arrow-function-lifecycle.js
new file mode 100644
index 0000000000000000000000000000000000000000..e56cb78601dd1e2528f1dc11764774bdf26e3ed4
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-arrow-function-lifecycle.js
@@ -0,0 +1,149 @@
+/**
+ * @fileoverview Lifecycle methods should be methods on the prototype, not class fields
+ * @author Tan Nguyen
+ */
+
+'use strict';
+
+const values = require('object.values');
+
+const Components = require('../util/Components');
+const astUtil = require('../util/ast');
+const componentUtil = require('../util/componentUtil');
+const docsUrl = require('../util/docsUrl');
+const lifecycleMethods = require('../util/lifecycleMethods');
+const report = require('../util/report');
+const eslintUtil = require('../util/eslint');
+
+const getSourceCode = eslintUtil.getSourceCode;
+const getText = eslintUtil.getText;
+
+function getRuleText(node) {
+ const params = node.value.params.map((p) => p.name);
+
+ if (node.type === 'Property') {
+ return `: function(${params.join(', ')}) `;
+ }
+
+ if (node.type === 'ClassProperty' || node.type === 'PropertyDefinition') {
+ return `(${params.join(', ')}) `;
+ }
+
+ return null;
+}
+
+const messages = {
+ lifecycle: '{{propertyName}} is a React lifecycle method, and should not be an arrow function or in a class field. Use an instance method instead.',
+};
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = {
+ meta: {
+ docs: {
+ description: 'Lifecycle methods should be methods on the prototype, not class fields',
+ category: 'Best Practices',
+ recommended: false,
+ url: docsUrl('no-arrow-function-lifecycle'),
+ },
+ messages,
+ schema: [],
+ fixable: 'code',
+ },
+
+ create: Components.detect((context, components) => {
+ /**
+ * @param {Array} properties list of component properties
+ */
+ function reportNoArrowFunctionLifecycle(properties) {
+ properties.forEach((node) => {
+ if (!node || !node.value) {
+ return;
+ }
+
+ const propertyName = astUtil.getPropertyName(node);
+ const nodeType = node.value.type;
+ const isLifecycleMethod = (
+ node.static && !componentUtil.isES5Component(node, context)
+ ? lifecycleMethods.static
+ : lifecycleMethods.instance
+ ).indexOf(propertyName) > -1;
+
+ if (nodeType === 'ArrowFunctionExpression' && isLifecycleMethod) {
+ const body = node.value.body;
+ const isBlockBody = body.type === 'BlockStatement';
+ const sourceCode = getSourceCode(context);
+
+ let nextComment = [];
+ let previousComment = [];
+ let bodyRange;
+ if (!isBlockBody) {
+ const previousToken = sourceCode.getTokenBefore(body);
+
+ if (sourceCode.getCommentsBefore) {
+ // eslint >=4.x
+ previousComment = sourceCode.getCommentsBefore(body);
+ } else {
+ // eslint 3.x
+ const potentialComment = sourceCode.getTokenBefore(body, { includeComments: true });
+ previousComment = previousToken === potentialComment ? [] : [potentialComment];
+ }
+
+ if (sourceCode.getCommentsAfter) {
+ // eslint >=4.x
+ nextComment = sourceCode.getCommentsAfter(body);
+ } else {
+ // eslint 3.x
+ const potentialComment = sourceCode.getTokenAfter(body, { includeComments: true });
+ const nextToken = sourceCode.getTokenAfter(body);
+ nextComment = nextToken === potentialComment ? [] : [potentialComment];
+ }
+ bodyRange = [
+ (previousComment.length > 0 ? previousComment[0] : body).range[0],
+ (nextComment.length > 0 ? nextComment[nextComment.length - 1] : body).range[1]
+ + (node.value.body.type === 'ObjectExpression' ? 1 : 0), // to account for a wrapped end paren
+ ];
+ }
+ const headRange = [
+ node.key.range[1],
+ (previousComment.length > 0 ? previousComment[0] : body).range[0],
+ ];
+ const hasSemi = node.value.expression && getText(context, node).slice(node.value.range[1] - node.range[0]) === ';';
+
+ report(
+ context,
+ messages.lifecycle,
+ 'lifecycle',
+ {
+ node,
+ data: {
+ propertyName,
+ },
+ fix(fixer) {
+ if (!sourceCode.getCommentsAfter) {
+ // eslint 3.x
+ return isBlockBody && fixer.replaceTextRange(headRange, getRuleText(node));
+ }
+ return [].concat(
+ fixer.replaceTextRange(headRange, getRuleText(node)),
+ isBlockBody ? [] : fixer.replaceTextRange(
+ [bodyRange[0], bodyRange[1] + (hasSemi ? 1 : 0)],
+ `{ return ${previousComment.map((x) => getText(context, x)).join('')}${getText(context, body)}${nextComment.map((x) => getText(context, x)).join('')}; }`
+ )
+ );
+ },
+ }
+ );
+ }
+ });
+ }
+
+ return {
+ 'Program:exit'() {
+ values(components.list()).forEach((component) => {
+ const properties = astUtil.getComponentProperties(component.node);
+ reportNoArrowFunctionLifecycle(properties);
+ });
+ },
+ };
+ }),
+};
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-children-prop.d.ts b/node_modules/eslint-plugin-react/lib/rules/no-children-prop.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..3e1dee067dbb5acef10036fe40e73c2de227f09d
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-children-prop.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=no-children-prop.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-children-prop.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/no-children-prop.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..d656c9331bd035d393d1f8e1df6978a83aba8ac6
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-children-prop.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"no-children-prop.d.ts","sourceRoot":"","sources":["no-children-prop.js"],"names":[],"mappings":"wBAuCW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-children-prop.js b/node_modules/eslint-plugin-react/lib/rules/no-children-prop.js
new file mode 100644
index 0000000000000000000000000000000000000000..84ccbbf3a6696b94a5791e5dc4839e4b54d274b5
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-children-prop.js
@@ -0,0 +1,125 @@
+/**
+ * @fileoverview Prevent passing of children as props
+ * @author Benjamin Stepp
+ */
+
+'use strict';
+
+const docsUrl = require('../util/docsUrl');
+const isCreateElement = require('../util/isCreateElement');
+const report = require('../util/report');
+
+// ------------------------------------------------------------------------------
+// Helpers
+// ------------------------------------------------------------------------------
+
+/**
+ * Checks if the node is a createElement call with a props literal.
+ * @param {ASTNode} node - The AST node being checked.
+ * @param {Context} context - The AST node being checked.
+ * @returns {boolean} - True if node is a createElement call with a props
+ * object literal, False if not.
+*/
+function isCreateElementWithProps(node, context) {
+ return isCreateElement(context, node)
+ && node.arguments.length > 1
+ && node.arguments[1].type === 'ObjectExpression';
+}
+
+// ------------------------------------------------------------------------------
+// Rule Definition
+// ------------------------------------------------------------------------------
+
+const messages = {
+ nestChildren: 'Do not pass children as props. Instead, nest children between the opening and closing tags.',
+ passChildrenAsArgs: 'Do not pass children as props. Instead, pass them as additional arguments to React.createElement.',
+ nestFunction: 'Do not nest a function between the opening and closing tags. Instead, pass it as a prop.',
+ passFunctionAsArgs: 'Do not pass a function as an additional argument to React.createElement. Instead, pass it as a prop.',
+};
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = {
+ meta: {
+ docs: {
+ description: 'Disallow passing of children as props',
+ category: 'Best Practices',
+ recommended: true,
+ url: docsUrl('no-children-prop'),
+ },
+
+ messages,
+
+ schema: [{
+ type: 'object',
+ properties: {
+ allowFunctions: {
+ type: 'boolean',
+ default: false,
+ },
+ },
+ additionalProperties: false,
+ }],
+ },
+ create(context) {
+ const configuration = context.options[0] || {};
+
+ function isFunction(node) {
+ return configuration.allowFunctions && (node.type === 'ArrowFunctionExpression' || node.type === 'FunctionExpression');
+ }
+
+ return {
+ JSXAttribute(node) {
+ if (node.name.name !== 'children') {
+ return;
+ }
+
+ const value = node.value;
+ if (value && value.type === 'JSXExpressionContainer' && isFunction(value.expression)) {
+ return;
+ }
+
+ report(context, messages.nestChildren, 'nestChildren', {
+ node,
+ });
+ },
+ CallExpression(node) {
+ if (!isCreateElementWithProps(node, context)) {
+ return;
+ }
+
+ const props = 'properties' in node.arguments[1] ? node.arguments[1].properties : undefined;
+ const childrenProp = props.find((prop) => (
+ 'key' in prop
+ && prop.key
+ && 'name' in prop.key
+ && prop.key.name === 'children'
+ ));
+
+ if (childrenProp) {
+ if ('value' in childrenProp && childrenProp.value && !isFunction(childrenProp.value)) {
+ report(context, messages.passChildrenAsArgs, 'passChildrenAsArgs', {
+ node,
+ });
+ }
+ } else if (node.arguments.length === 3) {
+ const children = node.arguments[2];
+ if (isFunction(children)) {
+ report(context, messages.passFunctionAsArgs, 'passFunctionAsArgs', {
+ node,
+ });
+ }
+ }
+ },
+ JSXElement(node) {
+ const children = node.children;
+ if (children && children.length === 1 && children[0].type === 'JSXExpressionContainer') {
+ if (isFunction(children[0].expression)) {
+ report(context, messages.nestFunction, 'nestFunction', {
+ node,
+ });
+ }
+ }
+ },
+ };
+ },
+};
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-danger-with-children.d.ts b/node_modules/eslint-plugin-react/lib/rules/no-danger-with-children.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..975773dd81de6d94cd05604cb625e9815ca03d43
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-danger-with-children.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=no-danger-with-children.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-danger-with-children.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/no-danger-with-children.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..718406f27e21cc68f5c1b07c1a14b1cf2e768077
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-danger-with-children.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"no-danger-with-children.d.ts","sourceRoot":"","sources":["no-danger-with-children.js"],"names":[],"mappings":"wBAmBW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-danger-with-children.js b/node_modules/eslint-plugin-react/lib/rules/no-danger-with-children.js
new file mode 100644
index 0000000000000000000000000000000000000000..3b01998502e7a6d5b4697b563cb6be571551a15c
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-danger-with-children.js
@@ -0,0 +1,157 @@
+/**
+ * @fileoverview Report when a DOM element is using both children and dangerouslySetInnerHTML
+ * @author David Petersen
+ */
+
+'use strict';
+
+const variableUtil = require('../util/variable');
+const jsxUtil = require('../util/jsx');
+const docsUrl = require('../util/docsUrl');
+const report = require('../util/report');
+
+// ------------------------------------------------------------------------------
+// Rule Definition
+// ------------------------------------------------------------------------------
+const messages = {
+ dangerWithChildren: 'Only set one of `children` or `props.dangerouslySetInnerHTML`',
+};
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = {
+ meta: {
+ docs: {
+ description: 'Disallow when a DOM element is using both children and dangerouslySetInnerHTML',
+ category: 'Possible Errors',
+ recommended: true,
+ url: docsUrl('no-danger-with-children'),
+ },
+
+ messages,
+
+ schema: [], // no options
+ },
+ create(context) {
+ function findSpreadVariable(node, name) {
+ return variableUtil.getVariableFromContext(context, node, name);
+ }
+ /**
+ * Takes a ObjectExpression and returns the value of the prop if it has it
+ * @param {object} node - ObjectExpression node
+ * @param {string} propName - name of the prop to look for
+ * @param {string[]} seenProps
+ * @returns {object | boolean}
+ */
+ function findObjectProp(node, propName, seenProps) {
+ if (!node.properties) {
+ return false;
+ }
+ return node.properties.find((prop) => {
+ if (prop.type === 'Property') {
+ return prop.key.name === propName;
+ }
+ if (prop.type === 'ExperimentalSpreadProperty' || prop.type === 'SpreadElement') {
+ const variable = findSpreadVariable(node, prop.argument.name);
+ if (variable && variable.defs.length && variable.defs[0].node.init) {
+ if (seenProps.indexOf(prop.argument.name) > -1) {
+ return false;
+ }
+ const newSeenProps = seenProps.concat(prop.argument.name || []);
+ return findObjectProp(variable.defs[0].node.init, propName, newSeenProps);
+ }
+ }
+ return false;
+ });
+ }
+
+ /**
+ * Takes a JSXElement and returns the value of the prop if it has it
+ * @param {object} node - JSXElement node
+ * @param {string} propName - name of the prop to look for
+ * @returns {object | boolean}
+ */
+ function findJsxProp(node, propName) {
+ const attributes = node.openingElement.attributes;
+ return attributes.find((attribute) => {
+ if (attribute.type === 'JSXSpreadAttribute') {
+ const variable = findSpreadVariable(node, attribute.argument.name);
+ if (variable && variable.defs.length && variable.defs[0].node.init) {
+ return findObjectProp(variable.defs[0].node.init, propName, []);
+ }
+ }
+ return attribute.name && attribute.name.name === propName;
+ });
+ }
+
+ /**
+ * Checks to see if a node is a line break
+ * @param {ASTNode} node The AST node being checked
+ * @returns {boolean} True if node is a line break, false if not
+ */
+ function isLineBreak(node) {
+ const isLiteral = node.type === 'Literal' || node.type === 'JSXText';
+ const isMultiline = node.loc.start.line !== node.loc.end.line;
+ const isWhiteSpaces = jsxUtil.isWhiteSpaces(node.value);
+
+ return isLiteral && isMultiline && isWhiteSpaces;
+ }
+
+ return {
+ JSXElement(node) {
+ let hasChildren = false;
+
+ if (node.children.length && !isLineBreak(node.children[0])) {
+ hasChildren = true;
+ } else if (findJsxProp(node, 'children')) {
+ hasChildren = true;
+ }
+
+ if (
+ node.openingElement.attributes
+ && hasChildren
+ && findJsxProp(node, 'dangerouslySetInnerHTML')
+ ) {
+ report(context, messages.dangerWithChildren, 'dangerWithChildren', {
+ node,
+ });
+ }
+ },
+ CallExpression(node) {
+ if (
+ node.callee
+ && node.callee.type === 'MemberExpression'
+ && 'name' in node.callee.property
+ && node.callee.property.name === 'createElement'
+ && node.arguments.length > 1
+ ) {
+ let hasChildren = false;
+
+ let props = node.arguments[1];
+
+ if (props.type === 'Identifier') {
+ const variable = variableUtil.getVariableFromContext(context, node, props.name);
+ if (variable && variable.defs.length && variable.defs[0].node.init) {
+ props = variable.defs[0].node.init;
+ }
+ }
+
+ const dangerously = findObjectProp(props, 'dangerouslySetInnerHTML', []);
+
+ if (node.arguments.length === 2) {
+ if (findObjectProp(props, 'children', [])) {
+ hasChildren = true;
+ }
+ } else {
+ hasChildren = true;
+ }
+
+ if (dangerously && hasChildren) {
+ report(context, messages.dangerWithChildren, 'dangerWithChildren', {
+ node,
+ });
+ }
+ }
+ },
+ };
+ },
+};
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-danger.d.ts b/node_modules/eslint-plugin-react/lib/rules/no-danger.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..c3953511f0e00f88ffb97df3290b03bd3e1cdb4b
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-danger.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=no-danger.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-danger.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/no-danger.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..30086713a079224efbf3dbae1a99424ac03f75ef
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-danger.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"no-danger.d.ts","sourceRoot":"","sources":["no-danger.js"],"names":[],"mappings":"wBA8CW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-danger.js b/node_modules/eslint-plugin-react/lib/rules/no-danger.js
new file mode 100644
index 0000000000000000000000000000000000000000..54dbed49cffd1912e2f99a141ff37515b8f1f7c2
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-danger.js
@@ -0,0 +1,96 @@
+/**
+ * @fileoverview Prevent usage of dangerous JSX props
+ * @author Scott Andrews
+ */
+
+'use strict';
+
+const has = require('hasown');
+const fromEntries = require('object.fromentries/polyfill')();
+const minimatch = require('minimatch');
+
+const docsUrl = require('../util/docsUrl');
+const jsxUtil = require('../util/jsx');
+const report = require('../util/report');
+
+// ------------------------------------------------------------------------------
+// Constants
+// ------------------------------------------------------------------------------
+
+const DANGEROUS_PROPERTY_NAMES = [
+ 'dangerouslySetInnerHTML',
+];
+
+const DANGEROUS_PROPERTIES = fromEntries(DANGEROUS_PROPERTY_NAMES.map((prop) => [prop, prop]));
+
+// ------------------------------------------------------------------------------
+// Helpers
+// ------------------------------------------------------------------------------
+
+/**
+ * Checks if a JSX attribute is dangerous.
+ * @param {string} name - Name of the attribute to check.
+ * @returns {boolean} Whether or not the attribute is dangerous.
+ */
+function isDangerous(name) {
+ return has(DANGEROUS_PROPERTIES, name);
+}
+
+// ------------------------------------------------------------------------------
+// Rule Definition
+// ------------------------------------------------------------------------------
+
+const messages = {
+ dangerousProp: 'Dangerous property \'{{name}}\' found',
+};
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = {
+ meta: {
+ docs: {
+ description: 'Disallow usage of dangerous JSX properties',
+ category: 'Best Practices',
+ recommended: false,
+ url: docsUrl('no-danger'),
+ },
+
+ messages,
+
+ schema: [{
+ type: 'object',
+ properties: {
+ customComponentNames: {
+ items: {
+ type: 'string',
+ },
+ minItems: 0,
+ type: 'array',
+ uniqueItems: true,
+ },
+ },
+ }],
+ },
+
+ create(context) {
+ const configuration = context.options[0] || {};
+ const customComponentNames = configuration.customComponentNames || [];
+
+ return {
+ JSXAttribute(node) {
+ const nodeName = node.parent.name;
+ const functionName = nodeName.name || `${nodeName.object.name}.${nodeName.property.name}`;
+
+ const enableCheckingCustomComponent = customComponentNames.some((name) => minimatch(functionName, name));
+
+ if ((enableCheckingCustomComponent || jsxUtil.isDOMComponent(node.parent)) && isDangerous(node.name.name)) {
+ report(context, messages.dangerousProp, 'dangerousProp', {
+ node,
+ data: {
+ name: node.name.name,
+ },
+ });
+ }
+ },
+ };
+ },
+};
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-deprecated.d.ts b/node_modules/eslint-plugin-react/lib/rules/no-deprecated.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..6820ee94b1dd8889242ac40a6c78d0f0f1a8f223
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-deprecated.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=no-deprecated.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-deprecated.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/no-deprecated.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..20b5970860774966349c181454b7b17bd44258a4
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-deprecated.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"no-deprecated.d.ts","sourceRoot":"","sources":["no-deprecated.js"],"names":[],"mappings":"wBAqHW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-deprecated.js b/node_modules/eslint-plugin-react/lib/rules/no-deprecated.js
new file mode 100644
index 0000000000000000000000000000000000000000..0c5931345f87841e43f0d28bf6f11e67e4842cef
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-deprecated.js
@@ -0,0 +1,271 @@
+/**
+ * @fileoverview Prevent usage of deprecated methods
+ * @author Yannick Croissant
+ * @author Scott Feeney
+ * @author Sergei Startsev
+ */
+
+'use strict';
+
+const entries = require('object.entries');
+const astUtil = require('../util/ast');
+const componentUtil = require('../util/componentUtil');
+const docsUrl = require('../util/docsUrl');
+const pragmaUtil = require('../util/pragma');
+const testReactVersion = require('../util/version').testReactVersion;
+const report = require('../util/report');
+const getText = require('../util/eslint').getText;
+
+// ------------------------------------------------------------------------------
+// Constants
+// ------------------------------------------------------------------------------
+
+const MODULES = {
+ react: ['React'],
+ 'react-addons-perf': ['ReactPerf', 'Perf'],
+ 'react-dom': ['ReactDOM'],
+ 'react-dom/server': ['ReactDOMServer'],
+};
+
+// ------------------------------------------------------------------------------
+// Rule Definition
+// ------------------------------------------------------------------------------
+
+function getDeprecated(pragma) {
+ const deprecated = {};
+ // 0.12.0
+ deprecated[`${pragma}.renderComponent`] = ['0.12.0', `${pragma}.render`];
+ deprecated[`${pragma}.renderComponentToString`] = ['0.12.0', `${pragma}.renderToString`];
+ deprecated[`${pragma}.renderComponentToStaticMarkup`] = ['0.12.0', `${pragma}.renderToStaticMarkup`];
+ deprecated[`${pragma}.isValidComponent`] = ['0.12.0', `${pragma}.isValidElement`];
+ deprecated[`${pragma}.PropTypes.component`] = ['0.12.0', `${pragma}.PropTypes.element`];
+ deprecated[`${pragma}.PropTypes.renderable`] = ['0.12.0', `${pragma}.PropTypes.node`];
+ deprecated[`${pragma}.isValidClass`] = ['0.12.0'];
+ deprecated['this.transferPropsTo'] = ['0.12.0', 'spread operator ({...})'];
+ // 0.13.0
+ deprecated[`${pragma}.addons.classSet`] = ['0.13.0', 'the npm module classnames'];
+ deprecated[`${pragma}.addons.cloneWithProps`] = ['0.13.0', `${pragma}.cloneElement`];
+ // 0.14.0
+ deprecated[`${pragma}.render`] = ['0.14.0', 'ReactDOM.render'];
+ deprecated[`${pragma}.unmountComponentAtNode`] = ['0.14.0', 'ReactDOM.unmountComponentAtNode'];
+ deprecated[`${pragma}.findDOMNode`] = ['0.14.0', 'ReactDOM.findDOMNode'];
+ deprecated[`${pragma}.renderToString`] = ['0.14.0', 'ReactDOMServer.renderToString'];
+ deprecated[`${pragma}.renderToStaticMarkup`] = ['0.14.0', 'ReactDOMServer.renderToStaticMarkup'];
+ // 15.0.0
+ deprecated[`${pragma}.addons.LinkedStateMixin`] = ['15.0.0'];
+ deprecated['ReactPerf.printDOM'] = ['15.0.0', 'ReactPerf.printOperations'];
+ deprecated['Perf.printDOM'] = ['15.0.0', 'Perf.printOperations'];
+ deprecated['ReactPerf.getMeasurementsSummaryMap'] = ['15.0.0', 'ReactPerf.getWasted'];
+ deprecated['Perf.getMeasurementsSummaryMap'] = ['15.0.0', 'Perf.getWasted'];
+ // 15.5.0
+ deprecated[`${pragma}.createClass`] = ['15.5.0', 'the npm module create-react-class'];
+ deprecated[`${pragma}.addons.TestUtils`] = ['15.5.0', 'ReactDOM.TestUtils'];
+ deprecated[`${pragma}.PropTypes`] = ['15.5.0', 'the npm module prop-types'];
+ // 15.6.0
+ deprecated[`${pragma}.DOM`] = ['15.6.0', 'the npm module react-dom-factories'];
+ // 16.9.0
+ // For now the following life-cycle methods are just legacy, not deprecated:
+ // `componentWillMount`, `componentWillReceiveProps`, `componentWillUpdate`
+ // https://github.com/yannickcr/eslint-plugin-react/pull/1750#issuecomment-425975934
+ deprecated.componentWillMount = [
+ '16.9.0',
+ 'UNSAFE_componentWillMount',
+ 'https://reactjs.org/docs/react-component.html#unsafe_componentwillmount. '
+ + 'Use https://github.com/reactjs/react-codemod#rename-unsafe-lifecycles to automatically update your components.',
+ ];
+ deprecated.componentWillReceiveProps = [
+ '16.9.0',
+ 'UNSAFE_componentWillReceiveProps',
+ 'https://reactjs.org/docs/react-component.html#unsafe_componentwillreceiveprops. '
+ + 'Use https://github.com/reactjs/react-codemod#rename-unsafe-lifecycles to automatically update your components.',
+ ];
+ deprecated.componentWillUpdate = [
+ '16.9.0',
+ 'UNSAFE_componentWillUpdate',
+ 'https://reactjs.org/docs/react-component.html#unsafe_componentwillupdate. '
+ + 'Use https://github.com/reactjs/react-codemod#rename-unsafe-lifecycles to automatically update your components.',
+ ];
+ // 18.0.0
+ // https://reactjs.org/blog/2022/03/08/react-18-upgrade-guide.html#deprecations
+ deprecated['ReactDOM.render'] = [
+ '18.0.0',
+ 'createRoot',
+ 'https://reactjs.org/link/switch-to-createroot',
+ ];
+ deprecated['ReactDOM.hydrate'] = [
+ '18.0.0',
+ 'hydrateRoot',
+ 'https://reactjs.org/link/switch-to-createroot',
+ ];
+ deprecated['ReactDOM.unmountComponentAtNode'] = [
+ '18.0.0',
+ 'root.unmount',
+ 'https://reactjs.org/link/switch-to-createroot',
+ ];
+ deprecated['ReactDOMServer.renderToNodeStream'] = [
+ '18.0.0',
+ 'renderToPipeableStream',
+ 'https://reactjs.org/docs/react-dom-server.html#rendertonodestream',
+ ];
+
+ return deprecated;
+}
+
+const messages = {
+ deprecated: '{{oldMethod}} is deprecated since React {{version}}{{newMethod}}{{refs}}',
+};
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = {
+ meta: {
+ docs: {
+ description: 'Disallow usage of deprecated methods',
+ category: 'Best Practices',
+ recommended: true,
+ url: docsUrl('no-deprecated'),
+ },
+
+ messages,
+
+ schema: [],
+ },
+
+ create(context) {
+ const pragma = pragmaUtil.getFromContext(context);
+ const deprecated = getDeprecated(pragma);
+
+ function isDeprecated(method) {
+ return (
+ deprecated
+ && deprecated[method]
+ && deprecated[method][0]
+ && testReactVersion(context, `>= ${deprecated[method][0]}`)
+ );
+ }
+
+ function checkDeprecation(node, methodName, methodNode) {
+ if (!isDeprecated(methodName)) {
+ return;
+ }
+ const version = deprecated[methodName][0];
+ const newMethod = deprecated[methodName][1];
+ const refs = deprecated[methodName][2];
+ report(context, messages.deprecated, 'deprecated', {
+ node: methodNode || node,
+ data: {
+ oldMethod: methodName,
+ version,
+ newMethod: newMethod ? `, use ${newMethod} instead` : '',
+ refs: refs ? `, see ${refs}` : '',
+ },
+ });
+ }
+
+ function getReactModuleName(node) {
+ let moduleName = false;
+ if (!node.init) {
+ return false;
+ }
+
+ entries(MODULES).some((entry) => {
+ const key = entry[0];
+ const moduleNames = entry[1];
+ if (
+ node.init.arguments
+ && node.init.arguments.length > 0
+ && node.init.arguments[0]
+ && key === node.init.arguments[0].value
+ ) {
+ moduleName = MODULES[key][0];
+ } else {
+ moduleName = moduleNames.find((name) => name === node.init.name);
+ }
+ return moduleName;
+ });
+
+ return moduleName;
+ }
+
+ /**
+ * Returns life cycle methods if available
+ * @param {ASTNode} node The AST node being checked.
+ * @returns {Array} The array of methods.
+ */
+ function getLifeCycleMethods(node) {
+ const properties = astUtil.getComponentProperties(node);
+ return properties.map((property) => ({
+ name: astUtil.getPropertyName(property),
+ node: astUtil.getPropertyNameNode(property),
+ }));
+ }
+
+ /**
+ * Checks life cycle methods
+ * @param {ASTNode} node The AST node being checked.
+ */
+ function checkLifeCycleMethods(node) {
+ if (
+ componentUtil.isES5Component(node, context)
+ || componentUtil.isES6Component(node, context)
+ ) {
+ const methods = getLifeCycleMethods(node);
+ methods.forEach((method) => checkDeprecation(node, method.name, method.node));
+ }
+ }
+
+ // --------------------------------------------------------------------------
+ // Public
+ // --------------------------------------------------------------------------
+
+ return {
+ MemberExpression(node) {
+ checkDeprecation(node, getText(context, node));
+ },
+
+ ImportDeclaration(node) {
+ const isReactImport = typeof MODULES[node.source.value] !== 'undefined';
+ if (!isReactImport) {
+ return;
+ }
+ node.specifiers.filter(((s) => 'imported' in s && s.imported)).forEach((specifier) => {
+ // TODO, semver-major: remove `in` check as part of jsdoc->tsdoc migration
+ checkDeprecation(node, 'imported' in specifier && 'name' in specifier.imported && `${MODULES[node.source.value][0]}.${specifier.imported.name}`, specifier);
+ });
+ },
+
+ VariableDeclarator(node) {
+ const reactModuleName = getReactModuleName(node);
+ const isRequire = node.init
+ && 'callee' in node.init
+ && node.init.callee
+ && 'name' in node.init.callee
+ && node.init.callee.name === 'require';
+ const isReactRequire = node.init
+ && 'arguments' in node.init
+ && node.init.arguments
+ && node.init.arguments.length
+ && typeof MODULES['value' in node.init.arguments[0] ? node.init.arguments[0].value : undefined] !== 'undefined';
+ const isDestructuring = node.id && node.id.type === 'ObjectPattern';
+
+ if (
+ !(isDestructuring && reactModuleName)
+ && !(isDestructuring && isRequire && isReactRequire)
+ ) {
+ return;
+ }
+
+ ('properties' in node.id ? node.id.properties : undefined).filter((p) => p.type !== 'RestElement' && p.key).forEach((property) => {
+ checkDeprecation(
+ node,
+ 'key' in property && 'name' in property.key && `${reactModuleName || pragma}.${property.key.name}`,
+ property
+ );
+ });
+ },
+
+ ClassDeclaration: checkLifeCycleMethods,
+ ClassExpression: checkLifeCycleMethods,
+ ObjectExpression: checkLifeCycleMethods,
+ };
+ },
+};
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-did-mount-set-state.d.ts b/node_modules/eslint-plugin-react/lib/rules/no-did-mount-set-state.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..a20eb747a1c20564465c2a0b4c349a7c32a79483
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-did-mount-set-state.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=no-did-mount-set-state.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-did-mount-set-state.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/no-did-mount-set-state.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..e257767c2eeb2755a96d01ed0d253e72a8434e19
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-did-mount-set-state.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"no-did-mount-set-state.d.ts","sourceRoot":"","sources":["no-did-mount-set-state.js"],"names":[],"mappings":"wBASW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-did-mount-set-state.js b/node_modules/eslint-plugin-react/lib/rules/no-did-mount-set-state.js
new file mode 100644
index 0000000000000000000000000000000000000000..ad70c3eb7be8c89ceabe7a0110b9b59f28c3e167
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-did-mount-set-state.js
@@ -0,0 +1,11 @@
+/**
+ * @fileoverview Prevent usage of setState in componentDidMount
+ * @author Yannick Croissant
+ */
+
+'use strict';
+
+const makeNoMethodSetStateRule = require('../util/makeNoMethodSetStateRule');
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = makeNoMethodSetStateRule('componentDidMount');
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-did-update-set-state.d.ts b/node_modules/eslint-plugin-react/lib/rules/no-did-update-set-state.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..0d0884d5a7ff7b9f2a5eb620921f0bed272125e2
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-did-update-set-state.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=no-did-update-set-state.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-did-update-set-state.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/no-did-update-set-state.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..97a150b763621c5f3d439ad1b0d7c773de101bab
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-did-update-set-state.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"no-did-update-set-state.d.ts","sourceRoot":"","sources":["no-did-update-set-state.js"],"names":[],"mappings":"wBASW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-did-update-set-state.js b/node_modules/eslint-plugin-react/lib/rules/no-did-update-set-state.js
new file mode 100644
index 0000000000000000000000000000000000000000..d297fb2648acd53ab49651ef566185d1aeee4e85
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-did-update-set-state.js
@@ -0,0 +1,11 @@
+/**
+ * @fileoverview Prevent usage of setState in componentDidUpdate
+ * @author Yannick Croissant
+ */
+
+'use strict';
+
+const makeNoMethodSetStateRule = require('../util/makeNoMethodSetStateRule');
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = makeNoMethodSetStateRule('componentDidUpdate');
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-direct-mutation-state.d.ts b/node_modules/eslint-plugin-react/lib/rules/no-direct-mutation-state.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..076e8a5d10a491c6ef798a610da28d6a69eaf781
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-direct-mutation-state.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=no-direct-mutation-state.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-direct-mutation-state.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/no-direct-mutation-state.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..4f5ed6425439161b28f1283d82758b08cb681fdb
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-direct-mutation-state.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"no-direct-mutation-state.d.ts","sourceRoot":"","sources":["no-direct-mutation-state.js"],"names":[],"mappings":"wBAuBW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-direct-mutation-state.js b/node_modules/eslint-plugin-react/lib/rules/no-direct-mutation-state.js
new file mode 100644
index 0000000000000000000000000000000000000000..761151fbb8743af15cf21f9d43be064488f4a12d
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-direct-mutation-state.js
@@ -0,0 +1,155 @@
+/**
+ * @fileoverview Prevent direct mutation of this.state
+ * @author David Petersen
+ * @author Nicolas Fernandez <@burabure>
+ */
+
+'use strict';
+
+const values = require('object.values');
+
+const Components = require('../util/Components');
+const componentUtil = require('../util/componentUtil');
+const docsUrl = require('../util/docsUrl');
+const report = require('../util/report');
+
+// ------------------------------------------------------------------------------
+// Rule Definition
+// ------------------------------------------------------------------------------
+
+const messages = {
+ noDirectMutation: 'Do not mutate state directly. Use setState().',
+};
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = {
+ meta: {
+ docs: {
+ description: 'Disallow direct mutation of this.state',
+ category: 'Possible Errors',
+ recommended: true,
+ url: docsUrl('no-direct-mutation-state'),
+ },
+
+ messages,
+ },
+
+ create: Components.detect((context, components, utils) => {
+ /**
+ * Checks if the component is valid
+ * @param {Object} component The component to process
+ * @returns {boolean} True if the component is valid, false if not.
+ */
+ function isValid(component) {
+ return !!component && !component.mutateSetState;
+ }
+
+ /**
+ * Reports undeclared proptypes for a given component
+ * @param {Object} component The component to process
+ */
+ function reportMutations(component) {
+ let mutation;
+ for (let i = 0, j = component.mutations.length; i < j; i++) {
+ mutation = component.mutations[i];
+ report(context, messages.noDirectMutation, 'noDirectMutation', {
+ node: mutation,
+ });
+ }
+ }
+
+ /**
+ * Walks through the MemberExpression to the top-most property.
+ * @param {Object} node The node to process
+ * @returns {Object} The outer-most MemberExpression
+ */
+ function getOuterMemberExpression(node) {
+ while (node.object && node.object.property) {
+ node = node.object;
+ }
+ return node;
+ }
+
+ /**
+ * Determine if we should currently ignore assignments in this component.
+ * @param {?Object} component The component to process
+ * @returns {boolean} True if we should skip assignment checks.
+ */
+ function shouldIgnoreComponent(component) {
+ return !component || (component.inConstructor && !component.inCallExpression);
+ }
+
+ // --------------------------------------------------------------------------
+ // Public
+ // --------------------------------------------------------------------------
+ return {
+ MethodDefinition(node) {
+ if (node.kind === 'constructor') {
+ components.set(node, {
+ inConstructor: true,
+ });
+ }
+ },
+
+ CallExpression(node) {
+ components.set(node, {
+ inCallExpression: true,
+ });
+ },
+
+ AssignmentExpression(node) {
+ const component = components.get(utils.getParentComponent(node));
+ if (shouldIgnoreComponent(component) || !node.left || !node.left.object) {
+ return;
+ }
+ const item = getOuterMemberExpression(node.left);
+ if (componentUtil.isStateMemberExpression(item)) {
+ const mutations = (component && component.mutations) || [];
+ mutations.push(node.left.object);
+ components.set(node, {
+ mutateSetState: true,
+ mutations,
+ });
+ }
+ },
+
+ UpdateExpression(node) {
+ const component = components.get(utils.getParentComponent(node));
+ if (shouldIgnoreComponent(component) || node.argument.type !== 'MemberExpression') {
+ return;
+ }
+ const item = getOuterMemberExpression(node.argument);
+ if (componentUtil.isStateMemberExpression(item)) {
+ const mutations = (component && component.mutations) || [];
+ mutations.push(item);
+ components.set(node, {
+ mutateSetState: true,
+ mutations,
+ });
+ }
+ },
+
+ 'CallExpression:exit'(node) {
+ components.set(node, {
+ inCallExpression: false,
+ });
+ },
+
+ 'MethodDefinition:exit'(node) {
+ if (node.kind === 'constructor') {
+ components.set(node, {
+ inConstructor: false,
+ });
+ }
+ },
+
+ 'Program:exit'() {
+ values(components.list())
+ .filter((component) => !isValid(component))
+ .forEach((component) => {
+ reportMutations(component);
+ });
+ },
+ };
+ }),
+};
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-find-dom-node.d.ts b/node_modules/eslint-plugin-react/lib/rules/no-find-dom-node.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..6ddc0a78ef1b89313f79119cfff55e908bb78bdc
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-find-dom-node.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=no-find-dom-node.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-find-dom-node.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/no-find-dom-node.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..7294175f5abfe596554007a0ce65e4c7548acc52
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-find-dom-node.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"no-find-dom-node.d.ts","sourceRoot":"","sources":["no-find-dom-node.js"],"names":[],"mappings":"wBAkBW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-find-dom-node.js b/node_modules/eslint-plugin-react/lib/rules/no-find-dom-node.js
new file mode 100644
index 0000000000000000000000000000000000000000..eaf9e53a464a1c73382b72c1892e42a3e05cf29e
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-find-dom-node.js
@@ -0,0 +1,56 @@
+/**
+ * @fileoverview Prevent usage of findDOMNode
+ * @author Yannick Croissant
+ */
+
+'use strict';
+
+const docsUrl = require('../util/docsUrl');
+const report = require('../util/report');
+
+// ------------------------------------------------------------------------------
+// Rule Definition
+// ------------------------------------------------------------------------------
+
+const messages = {
+ noFindDOMNode: 'Do not use findDOMNode. It doesn’t work with function components and is deprecated in StrictMode. See https://reactjs.org/docs/react-dom.html#finddomnode',
+};
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = {
+ meta: {
+ docs: {
+ description: 'Disallow usage of findDOMNode',
+ category: 'Best Practices',
+ recommended: true,
+ url: docsUrl('no-find-dom-node'),
+ },
+
+ messages,
+
+ schema: [],
+ },
+
+ create(context) {
+ return {
+ CallExpression(node) {
+ const callee = node.callee;
+
+ const isFindDOMNode = ('name' in callee && callee.name === 'findDOMNode') || (
+ 'property' in callee
+ && callee.property
+ && 'name' in callee.property
+ && callee.property.name === 'findDOMNode'
+ );
+
+ if (!isFindDOMNode) {
+ return;
+ }
+
+ report(context, messages.noFindDOMNode, 'noFindDOMNode', {
+ node: callee,
+ });
+ },
+ };
+ },
+};
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-invalid-html-attribute.d.ts b/node_modules/eslint-plugin-react/lib/rules/no-invalid-html-attribute.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..9baffdcef17e8622089d81b9cb63f9fea5846344
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-invalid-html-attribute.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=no-invalid-html-attribute.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-invalid-html-attribute.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/no-invalid-html-attribute.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..cfee0473db588572b22f475236bf1217927e7fd1
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-invalid-html-attribute.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"no-invalid-html-attribute.d.ts","sourceRoot":"","sources":["no-invalid-html-attribute.js"],"names":[],"mappings":"wBA+kBW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-invalid-html-attribute.js b/node_modules/eslint-plugin-react/lib/rules/no-invalid-html-attribute.js
new file mode 100644
index 0000000000000000000000000000000000000000..b8a14d1ab15b762d9bcea68b97310a4e3b46aab7
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-invalid-html-attribute.js
@@ -0,0 +1,654 @@
+/**
+ * @fileoverview Check if tag attributes to have non-valid value
+ * @author Sebastian Malton
+ */
+
+'use strict';
+
+const matchAll = require('string.prototype.matchall');
+const docsUrl = require('../util/docsUrl');
+const report = require('../util/report');
+
+// ------------------------------------------------------------------------------
+// Rule Definition
+// ------------------------------------------------------------------------------
+
+const rel = new Map([
+ ['alternate', new Set(['link', 'area', 'a'])],
+ ['apple-touch-icon', new Set(['link'])],
+ ['apple-touch-startup-image', new Set(['link'])],
+ ['author', new Set(['link', 'area', 'a'])],
+ ['bookmark', new Set(['area', 'a'])],
+ ['canonical', new Set(['link'])],
+ ['dns-prefetch', new Set(['link'])],
+ ['external', new Set(['area', 'a', 'form'])],
+ ['help', new Set(['link', 'area', 'a', 'form'])],
+ ['icon', new Set(['link'])],
+ ['license', new Set(['link', 'area', 'a', 'form'])],
+ ['manifest', new Set(['link'])],
+ ['mask-icon', new Set(['link'])],
+ ['modulepreload', new Set(['link'])],
+ ['next', new Set(['link', 'area', 'a', 'form'])],
+ ['nofollow', new Set(['area', 'a', 'form'])],
+ ['noopener', new Set(['area', 'a', 'form'])],
+ ['noreferrer', new Set(['area', 'a', 'form'])],
+ ['opener', new Set(['area', 'a', 'form'])],
+ ['pingback', new Set(['link'])],
+ ['preconnect', new Set(['link'])],
+ ['prefetch', new Set(['link'])],
+ ['preload', new Set(['link'])],
+ ['prerender', new Set(['link'])],
+ ['prev', new Set(['link', 'area', 'a', 'form'])],
+ ['search', new Set(['link', 'area', 'a', 'form'])],
+ ['shortcut', new Set(['link'])], // generally allowed but needs pair with "icon"
+ ['shortcut\u0020icon', new Set(['link'])],
+ ['stylesheet', new Set(['link'])],
+ ['tag', new Set(['area', 'a'])],
+]);
+
+const pairs = new Map([
+ ['shortcut', new Set(['icon'])],
+]);
+
+/**
+ * Map between attributes and a mapping between valid values and a set of tags they are valid on
+ * @type {Map>>}
+ */
+const VALID_VALUES = new Map([
+ ['rel', rel],
+]);
+
+/**
+ * Map between attributes and a mapping between pair-values and a set of values they are valid with
+ * @type {Map>>}
+ */
+const VALID_PAIR_VALUES = new Map([
+ ['rel', pairs],
+]);
+
+/**
+ * The set of all possible HTML elements. Used for skipping custom types
+ * @type {Set}
+ */
+const HTML_ELEMENTS = new Set([
+ 'a',
+ 'abbr',
+ 'acronym',
+ 'address',
+ 'applet',
+ 'area',
+ 'article',
+ 'aside',
+ 'audio',
+ 'b',
+ 'base',
+ 'basefont',
+ 'bdi',
+ 'bdo',
+ 'bgsound',
+ 'big',
+ 'blink',
+ 'blockquote',
+ 'body',
+ 'br',
+ 'button',
+ 'canvas',
+ 'caption',
+ 'center',
+ 'cite',
+ 'code',
+ 'col',
+ 'colgroup',
+ 'content',
+ 'data',
+ 'datalist',
+ 'dd',
+ 'del',
+ 'details',
+ 'dfn',
+ 'dialog',
+ 'dir',
+ 'div',
+ 'dl',
+ 'dt',
+ 'em',
+ 'embed',
+ 'fieldset',
+ 'figcaption',
+ 'figure',
+ 'font',
+ 'footer',
+ 'form',
+ 'frame',
+ 'frameset',
+ 'h1',
+ 'h2',
+ 'h3',
+ 'h4',
+ 'h5',
+ 'h6',
+ 'head',
+ 'header',
+ 'hgroup',
+ 'hr',
+ 'html',
+ 'i',
+ 'iframe',
+ 'image',
+ 'img',
+ 'input',
+ 'ins',
+ 'kbd',
+ 'keygen',
+ 'label',
+ 'legend',
+ 'li',
+ 'link',
+ 'main',
+ 'map',
+ 'mark',
+ 'marquee',
+ 'math',
+ 'menu',
+ 'menuitem',
+ 'meta',
+ 'meter',
+ 'nav',
+ 'nobr',
+ 'noembed',
+ 'noframes',
+ 'noscript',
+ 'object',
+ 'ol',
+ 'optgroup',
+ 'option',
+ 'output',
+ 'p',
+ 'param',
+ 'picture',
+ 'plaintext',
+ 'portal',
+ 'pre',
+ 'progress',
+ 'q',
+ 'rb',
+ 'rp',
+ 'rt',
+ 'rtc',
+ 'ruby',
+ 's',
+ 'samp',
+ 'script',
+ 'section',
+ 'select',
+ 'shadow',
+ 'slot',
+ 'small',
+ 'source',
+ 'spacer',
+ 'span',
+ 'strike',
+ 'strong',
+ 'style',
+ 'sub',
+ 'summary',
+ 'sup',
+ 'svg',
+ 'table',
+ 'tbody',
+ 'td',
+ 'template',
+ 'textarea',
+ 'tfoot',
+ 'th',
+ 'thead',
+ 'time',
+ 'title',
+ 'tr',
+ 'track',
+ 'tt',
+ 'u',
+ 'ul',
+ 'var',
+ 'video',
+ 'wbr',
+ 'xmp',
+]);
+
+/**
+* Map between attributes and set of tags that the attribute is valid on
+* @type {Map>}
+*/
+const COMPONENT_ATTRIBUTE_MAP = new Map([
+ ['rel', new Set(['link', 'a', 'area', 'form'])],
+]);
+
+/* eslint-disable eslint-plugin/no-unused-message-ids -- false positives, these messageIds are used */
+const messages = {
+ emptyIsMeaningless: 'An empty “{{attributeName}}” attribute is meaningless.',
+ neverValid: '“{{reportingValue}}” is never a valid “{{attributeName}}” attribute value.',
+ noEmpty: 'An empty “{{attributeName}}” attribute is meaningless.',
+ noMethod: 'The ”{{attributeName}}“ attribute cannot be a method.',
+ notAlone: '“{{reportingValue}}” must be directly followed by “{{missingValue}}”.',
+ notPaired: '“{{reportingValue}}” can not be directly followed by “{{secondValue}}” without “{{missingValue}}”.',
+ notValidFor: '“{{reportingValue}}” is not a valid “{{attributeName}}” attribute value for <{{elementName}}>.',
+ onlyMeaningfulFor: 'The ”{{attributeName}}“ attribute only has meaning on the tags: {{tagNames}}',
+ onlyStrings: '“{{attributeName}}” attribute only supports strings.',
+ spaceDelimited: '”{{attributeName}}“ attribute values should be space delimited.',
+ suggestRemoveDefault: '"remove {{attributeName}}"',
+ suggestRemoveEmpty: '"remove empty attribute {{attributeName}}"',
+ suggestRemoveInvalid: '“remove invalid attribute {{reportingValue}}”',
+ suggestRemoveWhitespaces: 'remove whitespaces in “{{attributeName}}”',
+ suggestRemoveNonString: 'remove non-string value in “{{attributeName}}”',
+};
+
+function splitIntoRangedParts(node, regex) {
+ const valueRangeStart = node.range[0] + 1; // the plus one is for the initial quote
+
+ return Array.from(matchAll(node.value, regex), (match) => {
+ const start = match.index + valueRangeStart;
+ const end = start + match[0].length;
+
+ return {
+ reportingValue: `${match[1]}`,
+ value: match[1],
+ range: [start, end],
+ };
+ });
+}
+
+function checkLiteralValueNode(context, attributeName, node, parentNode, parentNodeName) {
+ if (typeof node.value !== 'string') {
+ const data = { attributeName, reportingValue: node.value };
+
+ report(context, messages.onlyStrings, 'onlyStrings', {
+ node,
+ data,
+ suggest: [{
+ messageId: 'suggestRemoveNonString',
+ data,
+ fix(fixer) { return fixer.remove(parentNode); },
+ }],
+ });
+ return;
+ }
+
+ if (!node.value.trim()) {
+ const data = { attributeName, reportingValue: node.value };
+
+ report(context, messages.noEmpty, 'noEmpty', {
+ node,
+ data,
+ suggest: [{
+ messageId: 'suggestRemoveEmpty',
+ data,
+ fix(fixer) { return fixer.remove(node.parent); },
+ }],
+ });
+ return;
+ }
+
+ const singleAttributeParts = splitIntoRangedParts(node, /(\S+)/g);
+ singleAttributeParts.forEach((singlePart) => {
+ const allowedTags = VALID_VALUES.get(attributeName).get(singlePart.value);
+ const reportingValue = singlePart.reportingValue;
+
+ if (!allowedTags) {
+ const data = {
+ attributeName,
+ reportingValue,
+ };
+
+ const suggest = [{
+ messageId: 'suggestRemoveInvalid',
+ data,
+ fix(fixer) { return fixer.removeRange(singlePart.range); },
+ }];
+
+ report(context, messages.neverValid, 'neverValid', {
+ node,
+ data,
+ suggest,
+ });
+ } else if (!allowedTags.has(parentNodeName)) {
+ const data = {
+ attributeName,
+ reportingValue,
+ elementName: parentNodeName,
+ };
+
+ const suggest = [{
+ messageId: 'suggestRemoveInvalid',
+ data,
+ fix(fixer) { return fixer.removeRange(singlePart.range); },
+ }];
+
+ report(context, messages.notValidFor, 'notValidFor', {
+ node,
+ data,
+ suggest,
+ });
+ }
+ });
+
+ const allowedPairsForAttribute = VALID_PAIR_VALUES.get(attributeName);
+ if (allowedPairsForAttribute) {
+ const pairAttributeParts = splitIntoRangedParts(node, /(?=(\b\S+\s*\S+))/g);
+ pairAttributeParts.forEach((pairPart) => {
+ allowedPairsForAttribute.forEach((siblings, pairing) => {
+ const attributes = pairPart.reportingValue.split('\u0020');
+ const firstValue = attributes[0];
+ const secondValue = attributes[1];
+ if (firstValue === pairing) {
+ const lastValue = attributes[attributes.length - 1]; // in case of multiple white spaces
+ if (!siblings.has(lastValue)) {
+ const message = secondValue ? messages.notPaired : messages.notAlone;
+ const messageId = secondValue ? 'notPaired' : 'notAlone';
+ report(context, message, messageId, {
+ node,
+ data: {
+ reportingValue: firstValue,
+ secondValue,
+ missingValue: Array.from(siblings).join(', '),
+ },
+ suggest: false,
+ });
+ }
+ }
+ });
+ });
+ }
+
+ const whitespaceParts = splitIntoRangedParts(node, /(\s+)/g);
+ whitespaceParts.forEach((whitespacePart) => {
+ const data = { attributeName };
+
+ if (whitespacePart.range[0] === (node.range[0] + 1) || whitespacePart.range[1] === (node.range[1] - 1)) {
+ report(context, messages.spaceDelimited, 'spaceDelimited', {
+ node,
+ data,
+ suggest: [{
+ messageId: 'suggestRemoveWhitespaces',
+ data,
+ fix(fixer) { return fixer.removeRange(whitespacePart.range); },
+ }],
+ });
+ } else if (whitespacePart.value !== '\u0020') {
+ report(context, messages.spaceDelimited, 'spaceDelimited', {
+ node,
+ data,
+ suggest: [{
+ messageId: 'suggestRemoveWhitespaces',
+ data,
+ fix(fixer) { return fixer.replaceTextRange(whitespacePart.range, '\u0020'); },
+ }],
+ });
+ }
+ });
+}
+
+const DEFAULT_ATTRIBUTES = ['rel'];
+
+function checkAttribute(context, node) {
+ const attribute = node.name.name;
+
+ const parentNodeName = node.parent.name.name;
+ if (!COMPONENT_ATTRIBUTE_MAP.has(attribute) || !COMPONENT_ATTRIBUTE_MAP.get(attribute).has(parentNodeName)) {
+ const tagNames = Array.from(
+ COMPONENT_ATTRIBUTE_MAP.get(attribute).values(),
+ (tagName) => `"<${tagName}>"`
+ ).join(', ');
+ const data = {
+ attributeName: attribute,
+ tagNames,
+ };
+
+ report(context, messages.onlyMeaningfulFor, 'onlyMeaningfulFor', {
+ node: node.name,
+ data,
+ suggest: [{
+ messageId: 'suggestRemoveDefault',
+ data,
+ fix(fixer) { return fixer.remove(node); },
+ }],
+ });
+ return;
+ }
+
+ function fix(fixer) { return fixer.remove(node); }
+
+ if (!node.value) {
+ const data = { attributeName: attribute };
+
+ report(context, messages.emptyIsMeaningless, 'emptyIsMeaningless', {
+ node: node.name,
+ data,
+ suggest: [{
+ messageId: 'suggestRemoveEmpty',
+ data,
+ fix,
+ }],
+ });
+ return;
+ }
+
+ if (node.value.type === 'Literal') {
+ return checkLiteralValueNode(context, attribute, node.value, node, parentNodeName);
+ }
+
+ if (node.value.expression.type === 'Literal') {
+ return checkLiteralValueNode(context, attribute, node.value.expression, node, parentNodeName);
+ }
+
+ if (node.value.type !== 'JSXExpressionContainer') {
+ return;
+ }
+
+ if (node.value.expression.type === 'ObjectExpression') {
+ const data = { attributeName: attribute };
+
+ report(context, messages.onlyStrings, 'onlyStrings', {
+ node: node.value,
+ data,
+ suggest: [{
+ messageId: 'suggestRemoveDefault',
+ data,
+ fix,
+ }],
+ });
+ } else if (node.value.expression.type === 'Identifier' && node.value.expression.name === 'undefined') {
+ const data = { attributeName: attribute };
+
+ report(context, messages.onlyStrings, 'onlyStrings', {
+ node: node.value,
+ data,
+ suggest: [{
+ messageId: 'suggestRemoveDefault',
+ data,
+ fix,
+ }],
+ });
+ }
+}
+
+function isValidCreateElement(node) {
+ return node.callee
+ && node.callee.type === 'MemberExpression'
+ && node.callee.object.name === 'React'
+ && node.callee.property.name === 'createElement'
+ && node.arguments.length > 0;
+}
+
+function checkPropValidValue(context, node, value, attribute) {
+ const validTags = VALID_VALUES.get(attribute);
+
+ if (value.type !== 'Literal') {
+ return; // cannot check non-literals
+ }
+
+ const validTagSet = validTags.get(value.value);
+ if (!validTagSet) {
+ const data = {
+ attributeName: attribute,
+ reportingValue: value.value,
+ };
+
+ report(context, messages.neverValid, 'neverValid', {
+ node: value,
+ data,
+ suggest: [{
+ messageId: 'suggestRemoveInvalid',
+ data,
+ fix(fixer) { return fixer.replaceText(value, value.raw.replace(value.value, '')); },
+ }],
+ });
+ } else if (!validTagSet.has(node.arguments[0].value)) {
+ report(context, messages.notValidFor, 'notValidFor', {
+ node: value,
+ data: {
+ attributeName: attribute,
+ reportingValue: value.raw,
+ elementName: node.arguments[0].value,
+ },
+ suggest: false,
+ });
+ }
+}
+
+/**
+ *
+ * @param {*} context
+ * @param {*} node
+ * @param {string} attribute
+ */
+function checkCreateProps(context, node, attribute) {
+ const propsArg = node.arguments[1];
+
+ if (!propsArg || propsArg.type !== 'ObjectExpression') {
+ return; // can't check variables, computed, or shorthands
+ }
+
+ for (const prop of propsArg.properties) {
+ if (!prop.key || prop.key.type !== 'Identifier') {
+ // eslint-disable-next-line no-continue
+ continue; // cannot check computed keys
+ }
+
+ if (prop.key.name !== attribute) {
+ // eslint-disable-next-line no-continue
+ continue; // ignore not this attribute
+ }
+
+ if (!COMPONENT_ATTRIBUTE_MAP.get(attribute).has(node.arguments[0].value)) {
+ const tagNames = Array.from(
+ COMPONENT_ATTRIBUTE_MAP.get(attribute).values(),
+ (tagName) => `"<${tagName}>"`
+ ).join(', ');
+
+ report(context, messages.onlyMeaningfulFor, 'onlyMeaningfulFor', {
+ node: prop.key,
+ data: {
+ attributeName: attribute,
+ tagNames,
+ },
+ suggest: false,
+ });
+
+ // eslint-disable-next-line no-continue
+ continue;
+ }
+
+ if (prop.method) {
+ report(context, messages.noMethod, 'noMethod', {
+ node: prop,
+ data: {
+ attributeName: attribute,
+ },
+ suggest: false,
+ });
+
+ // eslint-disable-next-line no-continue
+ continue;
+ }
+
+ if (prop.shorthand || prop.computed) {
+ // eslint-disable-next-line no-continue
+ continue; // cannot check these
+ }
+
+ if (prop.value.type === 'ArrayExpression') {
+ prop.value.elements.forEach((value) => {
+ checkPropValidValue(context, node, value, attribute);
+ });
+
+ // eslint-disable-next-line no-continue
+ continue;
+ }
+
+ checkPropValidValue(context, node, prop.value, attribute);
+ }
+}
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = {
+ meta: {
+ docs: {
+ description: 'Disallow usage of invalid attributes',
+ category: 'Possible Errors',
+ url: docsUrl('no-invalid-html-attribute'),
+ },
+ messages,
+ schema: [{
+ type: 'array',
+ uniqueItems: true,
+ items: {
+ enum: ['rel'],
+ },
+ }],
+ type: 'suggestion',
+ hasSuggestions: true, // eslint-disable-line eslint-plugin/require-meta-has-suggestions
+ },
+
+ create(context) {
+ return {
+ JSXAttribute(node) {
+ const attributes = new Set(context.options[0] || DEFAULT_ATTRIBUTES);
+
+ // ignore attributes that aren't configured to be checked
+ if (!attributes.has(node.name.name)) {
+ return;
+ }
+
+ // ignore non-HTML elements
+ if (!HTML_ELEMENTS.has(node.parent.name.name)) {
+ return;
+ }
+
+ checkAttribute(context, node);
+ },
+
+ CallExpression(node) {
+ if (!isValidCreateElement(node)) {
+ return;
+ }
+
+ const elemNameArg = node.arguments[0];
+
+ if (!elemNameArg || elemNameArg.type !== 'Literal') {
+ return; // can only check literals
+ }
+
+ // ignore non-HTML elements
+ if (typeof elemNameArg.value === 'string' && !HTML_ELEMENTS.has(elemNameArg.value)) {
+ return;
+ }
+
+ const attributes = new Set(context.options[0] || DEFAULT_ATTRIBUTES);
+
+ attributes.forEach((attribute) => {
+ checkCreateProps(context, node, attribute);
+ });
+ },
+ };
+ },
+};
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-is-mounted.d.ts b/node_modules/eslint-plugin-react/lib/rules/no-is-mounted.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..f4892198b82b67dbdb6a24539d6e6d94e184e286
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-is-mounted.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=no-is-mounted.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-is-mounted.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/no-is-mounted.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..df27f4a8419324c77297924a82a0f237bbdffb91
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-is-mounted.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"no-is-mounted.d.ts","sourceRoot":"","sources":["no-is-mounted.js"],"names":[],"mappings":"wBAmBW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-is-mounted.js b/node_modules/eslint-plugin-react/lib/rules/no-is-mounted.js
new file mode 100644
index 0000000000000000000000000000000000000000..24d9a37d02b00eee06fda59a79b58b6dda990d1f
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-is-mounted.js
@@ -0,0 +1,61 @@
+/**
+ * @fileoverview Prevent usage of isMounted
+ * @author Joe Lencioni
+ */
+
+'use strict';
+
+const docsUrl = require('../util/docsUrl');
+const getAncestors = require('../util/eslint').getAncestors;
+const report = require('../util/report');
+
+// ------------------------------------------------------------------------------
+// Rule Definition
+// ------------------------------------------------------------------------------
+
+const messages = {
+ noIsMounted: 'Do not use isMounted',
+};
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = {
+ meta: {
+ docs: {
+ description: 'Disallow usage of isMounted',
+ category: 'Best Practices',
+ recommended: true,
+ url: docsUrl('no-is-mounted'),
+ },
+
+ messages,
+
+ schema: [],
+ },
+
+ create(context) {
+ return {
+ CallExpression(node) {
+ const callee = node.callee;
+ if (callee.type !== 'MemberExpression') {
+ return;
+ }
+ if (
+ callee.object.type !== 'ThisExpression'
+ || !('name' in callee.property)
+ || callee.property.name !== 'isMounted'
+ ) {
+ return;
+ }
+ const ancestors = getAncestors(context, node);
+ for (let i = 0, j = ancestors.length; i < j; i++) {
+ if (ancestors[i].type === 'Property' || ancestors[i].type === 'MethodDefinition') {
+ report(context, messages.noIsMounted, 'noIsMounted', {
+ node: callee,
+ });
+ break;
+ }
+ }
+ },
+ };
+ },
+};
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-multi-comp.d.ts b/node_modules/eslint-plugin-react/lib/rules/no-multi-comp.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..73770afd1816d7fe066fee88d15e055692271ffc
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-multi-comp.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=no-multi-comp.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-multi-comp.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/no-multi-comp.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..b62343ee261033db8a794857cb483df180137888
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-multi-comp.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"no-multi-comp.d.ts","sourceRoot":"","sources":["no-multi-comp.js"],"names":[],"mappings":"wBAqBW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-multi-comp.js b/node_modules/eslint-plugin-react/lib/rules/no-multi-comp.js
new file mode 100644
index 0000000000000000000000000000000000000000..8cf73c90bce43a80b39fb30c3255c9d7b1983be4
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-multi-comp.js
@@ -0,0 +1,81 @@
+/**
+ * @fileoverview Prevent multiple component definition per file
+ * @author Yannick Croissant
+ */
+
+'use strict';
+
+const values = require('object.values');
+
+const Components = require('../util/Components');
+const docsUrl = require('../util/docsUrl');
+const report = require('../util/report');
+
+// ------------------------------------------------------------------------------
+// Rule Definition
+// ------------------------------------------------------------------------------
+
+const messages = {
+ onlyOneComponent: 'Declare only one React component per file',
+};
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = {
+ meta: {
+ docs: {
+ description: 'Disallow multiple component definition per file',
+ category: 'Stylistic Issues',
+ recommended: false,
+ url: docsUrl('no-multi-comp'),
+ },
+
+ messages,
+
+ schema: [{
+ type: 'object',
+ properties: {
+ ignoreStateless: {
+ default: false,
+ type: 'boolean',
+ },
+ },
+ additionalProperties: false,
+ }],
+ },
+
+ create: Components.detect((context, components, utils) => {
+ const configuration = context.options[0] || {};
+ const ignoreStateless = configuration.ignoreStateless || false;
+
+ /**
+ * Checks if the component is ignored
+ * @param {Object} component The component being checked.
+ * @returns {boolean} True if the component is ignored, false if not.
+ */
+ function isIgnored(component) {
+ return (
+ ignoreStateless && (
+ /Function/.test(component.node.type)
+ || utils.isPragmaComponentWrapper(component.node)
+ )
+ );
+ }
+
+ return {
+ 'Program:exit'() {
+ if (components.length() <= 1) {
+ return;
+ }
+
+ values(components.list())
+ .filter((component) => !isIgnored(component))
+ .slice(1)
+ .forEach((component) => {
+ report(context, messages.onlyOneComponent, 'onlyOneComponent', {
+ node: component.node,
+ });
+ });
+ },
+ };
+ }),
+};
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-namespace.d.ts b/node_modules/eslint-plugin-react/lib/rules/no-namespace.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..1c55685dbda6858f3486f2827d748b4344def12e
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-namespace.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=no-namespace.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-namespace.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/no-namespace.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..b56a75f79009c4358c2365cf68526174fe312972
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-namespace.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"no-namespace.d.ts","sourceRoot":"","sources":["no-namespace.js"],"names":[],"mappings":"wBAoBW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-namespace.js b/node_modules/eslint-plugin-react/lib/rules/no-namespace.js
new file mode 100644
index 0000000000000000000000000000000000000000..20ca5d93241c1956cbbb079287ee64ae1aec2ed6
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-namespace.js
@@ -0,0 +1,62 @@
+/**
+ * @fileoverview Enforce that namespaces are not used in React elements
+ * @author Yacine Hmito
+ */
+
+'use strict';
+
+const elementType = require('jsx-ast-utils/elementType');
+const docsUrl = require('../util/docsUrl');
+const isCreateElement = require('../util/isCreateElement');
+const report = require('../util/report');
+
+// ------------------------------------------------------------------------------
+// Rule Definition
+// ------------------------------------------------------------------------------
+
+const messages = {
+ noNamespace: 'React component {{name}} must not be in a namespace, as React does not support them',
+};
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = {
+ meta: {
+ docs: {
+ description: 'Enforce that namespaces are not used in React elements',
+ category: 'Possible Errors',
+ recommended: false,
+ url: docsUrl('no-namespace'),
+ },
+
+ messages,
+
+ schema: [],
+ },
+
+ create(context) {
+ return {
+ CallExpression(node) {
+ if (isCreateElement(context, node) && node.arguments.length > 0 && node.arguments[0].type === 'Literal') {
+ const name = node.arguments[0].value;
+ if (typeof name !== 'string' || name.indexOf(':') === -1) return undefined;
+ report(context, messages.noNamespace, 'noNamespace', {
+ node,
+ data: {
+ name,
+ },
+ });
+ }
+ },
+ JSXOpeningElement(node) {
+ const name = elementType(node);
+ if (typeof name !== 'string' || name.indexOf(':') === -1) return undefined;
+ report(context, messages.noNamespace, 'noNamespace', {
+ node,
+ data: {
+ name,
+ },
+ });
+ },
+ };
+ },
+};
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-object-type-as-default-prop.d.ts b/node_modules/eslint-plugin-react/lib/rules/no-object-type-as-default-prop.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..03a21901c4c5ff731fcee12ad899079e7cc8c173
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-object-type-as-default-prop.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=no-object-type-as-default-prop.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-object-type-as-default-prop.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/no-object-type-as-default-prop.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..218aa6e29e36d5c73dd39ad7a1e37272e237e56a
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-object-type-as-default-prop.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"no-object-type-as-default-prop.d.ts","sourceRoot":"","sources":["no-object-type-as-default-prop.js"],"names":[],"mappings":"wBAiFW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-object-type-as-default-prop.js b/node_modules/eslint-plugin-react/lib/rules/no-object-type-as-default-prop.js
new file mode 100644
index 0000000000000000000000000000000000000000..2683bfea4cba4c9cb4e286954d164731fc949127
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-object-type-as-default-prop.js
@@ -0,0 +1,105 @@
+/**
+ * @fileoverview Prevent usage of referential-type variables as default param in functional component
+ * @author Chang Yan
+ */
+
+'use strict';
+
+const values = require('object.values');
+
+const Components = require('../util/Components');
+const docsUrl = require('../util/docsUrl');
+const astUtil = require('../util/ast');
+const report = require('../util/report');
+
+const FORBIDDEN_TYPES_MAP = {
+ ArrowFunctionExpression: 'arrow function',
+ FunctionExpression: 'function expression',
+ ObjectExpression: 'object literal',
+ ArrayExpression: 'array literal',
+ ClassExpression: 'class expression',
+ NewExpression: 'construction expression',
+ JSXElement: 'JSX element',
+};
+
+const FORBIDDEN_TYPES = new Set(Object.keys(FORBIDDEN_TYPES_MAP));
+const MESSAGE_ID = 'forbiddenTypeDefaultParam';
+
+const messages = {
+ [MESSAGE_ID]: '{{propName}} has a/an {{forbiddenType}} as default prop. This could lead to potential infinite render loop in React. Use a variable reference instead of {{forbiddenType}}.',
+};
+function hasUsedObjectDestructuringSyntax(params) {
+ return (
+ params != null
+ && params.length >= 1
+ && params[0].type === 'ObjectPattern'
+ );
+}
+
+function verifyDefaultPropsDestructuring(context, properties) {
+ // Loop through each of the default params
+ properties.filter((prop) => prop.type === 'Property' && prop.value.type === 'AssignmentPattern').forEach((prop) => {
+ const propName = prop.key.name;
+ const propDefaultValue = prop.value;
+
+ const propDefaultValueType = propDefaultValue.right.type;
+
+ if (
+ propDefaultValueType === 'Literal'
+ && propDefaultValue.right.regex != null
+ ) {
+ report(context, messages[MESSAGE_ID], MESSAGE_ID, {
+ node: propDefaultValue,
+ data: {
+ propName,
+ forbiddenType: 'regex literal',
+ },
+ });
+ } else if (
+ astUtil.isCallExpression(propDefaultValue.right)
+ && propDefaultValue.right.callee.type === 'Identifier'
+ && propDefaultValue.right.callee.name === 'Symbol'
+ ) {
+ report(context, messages[MESSAGE_ID], MESSAGE_ID, {
+ node: propDefaultValue,
+ data: {
+ propName,
+ forbiddenType: 'Symbol literal',
+ },
+ });
+ } else if (FORBIDDEN_TYPES.has(propDefaultValueType)) {
+ report(context, messages[MESSAGE_ID], MESSAGE_ID, {
+ node: propDefaultValue,
+ data: {
+ propName,
+ forbiddenType: FORBIDDEN_TYPES_MAP[propDefaultValueType],
+ },
+ });
+ }
+ });
+}
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = {
+ meta: {
+ docs: {
+ description: 'Disallow usage of referential-type variables as default param in functional component',
+ category: 'Best Practices',
+ recommended: false,
+ url: docsUrl('no-object-type-as-default-prop'),
+ },
+ messages,
+ },
+ create: Components.detect((context, components) => ({
+ 'Program:exit'() {
+ const list = components.list();
+ values(list)
+ .filter((component) => hasUsedObjectDestructuringSyntax(component.node.params))
+ .forEach((component) => {
+ const node = component.node;
+ const properties = node.params[0].properties;
+ verifyDefaultPropsDestructuring(context, properties);
+ });
+ },
+ })),
+};
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-redundant-should-component-update.d.ts b/node_modules/eslint-plugin-react/lib/rules/no-redundant-should-component-update.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..721c683ffabb04c71cfa18f14c91fdb79a1a2e8f
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-redundant-should-component-update.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=no-redundant-should-component-update.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-redundant-should-component-update.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/no-redundant-should-component-update.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..8e2e6b17fe0cdc874bd4cf7819dc33e92e493e1d
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-redundant-should-component-update.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"no-redundant-should-component-update.d.ts","sourceRoot":"","sources":["no-redundant-should-component-update.js"],"names":[],"mappings":"wBAmBW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-redundant-should-component-update.js b/node_modules/eslint-plugin-react/lib/rules/no-redundant-should-component-update.js
new file mode 100644
index 0000000000000000000000000000000000000000..e7a439d8e836a098621c92407a585a9ed9568c13
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-redundant-should-component-update.js
@@ -0,0 +1,88 @@
+/**
+ * @fileoverview Flag shouldComponentUpdate when extending PureComponent
+ */
+
+'use strict';
+
+const astUtil = require('../util/ast');
+const componentUtil = require('../util/componentUtil');
+const docsUrl = require('../util/docsUrl');
+const report = require('../util/report');
+
+// ------------------------------------------------------------------------------
+// Rule Definition
+// ------------------------------------------------------------------------------
+
+const messages = {
+ noShouldCompUpdate: '{{component}} does not need shouldComponentUpdate when extending React.PureComponent.',
+};
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = {
+ meta: {
+ docs: {
+ description: 'Disallow usage of shouldComponentUpdate when extending React.PureComponent',
+ category: 'Possible Errors',
+ recommended: false,
+ url: docsUrl('no-redundant-should-component-update'),
+ },
+
+ messages,
+
+ schema: [],
+ },
+
+ create(context) {
+ /**
+ * Checks for shouldComponentUpdate property
+ * @param {ASTNode} node The AST node being checked.
+ * @returns {boolean} Whether or not the property exists.
+ */
+ function hasShouldComponentUpdate(node) {
+ const properties = astUtil.getComponentProperties(node);
+ return properties.some((property) => {
+ const name = astUtil.getPropertyName(property);
+ return name === 'shouldComponentUpdate';
+ });
+ }
+
+ /**
+ * Get name of node if available
+ * @param {ASTNode} node The AST node being checked.
+ * @return {string} The name of the node
+ */
+ function getNodeName(node) {
+ if (node.id) {
+ return node.id.name;
+ }
+ if (node.parent && node.parent.id) {
+ return node.parent.id.name;
+ }
+ return '';
+ }
+
+ /**
+ * Checks for violation of rule
+ * @param {ASTNode} node The AST node being checked.
+ */
+ function checkForViolation(node) {
+ if (componentUtil.isPureComponent(node, context)) {
+ const hasScu = hasShouldComponentUpdate(node);
+ if (hasScu) {
+ const className = getNodeName(node);
+ report(context, messages.noShouldCompUpdate, 'noShouldCompUpdate', {
+ node,
+ data: {
+ component: className,
+ },
+ });
+ }
+ }
+ }
+
+ return {
+ ClassDeclaration: checkForViolation,
+ ClassExpression: checkForViolation,
+ };
+ },
+};
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-render-return-value.d.ts b/node_modules/eslint-plugin-react/lib/rules/no-render-return-value.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..e3fc9f179648e9fe029fab0af7d87c7aa9462f81
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-render-return-value.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=no-render-return-value.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-render-return-value.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/no-render-return-value.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..e8929411742cf8da09215b9731a1c6cc78ace921
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-render-return-value.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"no-render-return-value.d.ts","sourceRoot":"","sources":["no-render-return-value.js"],"names":[],"mappings":"wBAmBW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-render-return-value.js b/node_modules/eslint-plugin-react/lib/rules/no-render-return-value.js
new file mode 100644
index 0000000000000000000000000000000000000000..9e0f9d4046768885bc6a9103d66aa35408f03b96
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-render-return-value.js
@@ -0,0 +1,82 @@
+/**
+ * @fileoverview Prevent usage of the return value of React.render
+ * @author Dustan Kasten
+ */
+
+'use strict';
+
+const testReactVersion = require('../util/version').testReactVersion;
+const docsUrl = require('../util/docsUrl');
+const report = require('../util/report');
+
+// ------------------------------------------------------------------------------
+// Rule Definition
+// ------------------------------------------------------------------------------
+
+const messages = {
+ noReturnValue: 'Do not depend on the return value from {{node}}.render',
+};
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = {
+ meta: {
+ docs: {
+ description: 'Disallow usage of the return value of ReactDOM.render',
+ category: 'Best Practices',
+ recommended: true,
+ url: docsUrl('no-render-return-value'),
+ },
+
+ messages,
+
+ schema: [],
+ },
+
+ create(context) {
+ // --------------------------------------------------------------------------
+ // Public
+ // --------------------------------------------------------------------------
+
+ let calleeObjectName = /^ReactDOM$/;
+ if (testReactVersion(context, '>= 15.0.0')) {
+ calleeObjectName = /^ReactDOM$/;
+ } else if (testReactVersion(context, '^0.14.0')) {
+ calleeObjectName = /^React(DOM)?$/;
+ } else if (testReactVersion(context, '^0.13.0')) {
+ calleeObjectName = /^React$/;
+ }
+
+ return {
+ CallExpression(node) {
+ const callee = node.callee;
+ const parent = node.parent;
+ if (callee.type !== 'MemberExpression') {
+ return;
+ }
+
+ if (
+ callee.object.type !== 'Identifier'
+ || !calleeObjectName.test(callee.object.name)
+ || (!('name' in callee.property) || callee.property.name !== 'render')
+ ) {
+ return;
+ }
+
+ if (
+ parent.type === 'VariableDeclarator'
+ || parent.type === 'Property'
+ || parent.type === 'ReturnStatement'
+ || parent.type === 'ArrowFunctionExpression'
+ || parent.type === 'AssignmentExpression'
+ ) {
+ report(context, messages.noReturnValue, 'noReturnValue', {
+ node: callee,
+ data: {
+ node: callee.object.name,
+ },
+ });
+ }
+ },
+ };
+ },
+};
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-set-state.d.ts b/node_modules/eslint-plugin-react/lib/rules/no-set-state.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..d9825f5b1433c7f9494b78f58f77a040e815cc44
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-set-state.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=no-set-state.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-set-state.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/no-set-state.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..f47d09a5d37d0a0a04f517c01c371188c719083f
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-set-state.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"no-set-state.d.ts","sourceRoot":"","sources":["no-set-state.js"],"names":[],"mappings":"wBAqBW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-set-state.js b/node_modules/eslint-plugin-react/lib/rules/no-set-state.js
new file mode 100644
index 0000000000000000000000000000000000000000..44967bf03cba12524a79e871f2256c3b94579f42
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-set-state.js
@@ -0,0 +1,88 @@
+/**
+ * @fileoverview Prevent usage of setState
+ * @author Mark Dalgleish
+ */
+
+'use strict';
+
+const values = require('object.values');
+
+const Components = require('../util/Components');
+const docsUrl = require('../util/docsUrl');
+const report = require('../util/report');
+
+// ------------------------------------------------------------------------------
+// Rule Definition
+// ------------------------------------------------------------------------------
+
+const messages = {
+ noSetState: 'Do not use setState',
+};
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = {
+ meta: {
+ docs: {
+ description: 'Disallow usage of setState',
+ category: 'Stylistic Issues',
+ recommended: false,
+ url: docsUrl('no-set-state'),
+ },
+
+ messages,
+
+ schema: [],
+ },
+
+ create: Components.detect((context, components, utils) => {
+ /**
+ * Checks if the component is valid
+ * @param {Object} component The component to process
+ * @returns {boolean} True if the component is valid, false if not.
+ */
+ function isValid(component) {
+ return !!component && !component.useSetState;
+ }
+
+ /**
+ * Reports usages of setState for a given component
+ * @param {Object} component The component to process
+ */
+ function reportSetStateUsages(component) {
+ for (let i = 0, j = component.setStateUsages.length; i < j; i++) {
+ const setStateUsage = component.setStateUsages[i];
+ report(context, messages.noSetState, 'noSetState', {
+ node: setStateUsage,
+ });
+ }
+ }
+
+ return {
+ CallExpression(node) {
+ const callee = node.callee;
+ if (
+ callee.type !== 'MemberExpression'
+ || callee.object.type !== 'ThisExpression'
+ || callee.property.name !== 'setState'
+ ) {
+ return;
+ }
+ const component = components.get(utils.getParentComponent(node));
+ const setStateUsages = (component && component.setStateUsages) || [];
+ setStateUsages.push(callee);
+ components.set(node, {
+ useSetState: true,
+ setStateUsages,
+ });
+ },
+
+ 'Program:exit'() {
+ values(components.list())
+ .filter((component) => !isValid(component))
+ .forEach((component) => {
+ reportSetStateUsages(component);
+ });
+ },
+ };
+ }),
+};
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-string-refs.d.ts b/node_modules/eslint-plugin-react/lib/rules/no-string-refs.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..8e44ed1d84beacc9d9a5c80e9130a3b3476ecdea
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-string-refs.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=no-string-refs.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-string-refs.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/no-string-refs.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..6af2d5b2ee5d52ddcee81576c0144a9f735888aa
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-string-refs.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"no-string-refs.d.ts","sourceRoot":"","sources":["no-string-refs.js"],"names":[],"mappings":"wBAqBW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-string-refs.js b/node_modules/eslint-plugin-react/lib/rules/no-string-refs.js
new file mode 100644
index 0000000000000000000000000000000000000000..145ad25780cf2ca507649de1779e2e6a3b617dab
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-string-refs.js
@@ -0,0 +1,117 @@
+/**
+ * @fileoverview Prevent string definitions for references and prevent referencing this.refs
+ * @author Tom Hastjarjanto
+ */
+
+'use strict';
+
+const componentUtil = require('../util/componentUtil');
+const docsUrl = require('../util/docsUrl');
+const report = require('../util/report');
+const testReactVersion = require('../util/version').testReactVersion;
+
+// ------------------------------------------------------------------------------
+// Rule Definition
+// ------------------------------------------------------------------------------
+
+const messages = {
+ thisRefsDeprecated: 'Using this.refs is deprecated.',
+ stringInRefDeprecated: 'Using string literals in ref attributes is deprecated.',
+};
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = {
+ meta: {
+ docs: {
+ description: 'Disallow using string references',
+ category: 'Best Practices',
+ recommended: true,
+ url: docsUrl('no-string-refs'),
+ },
+
+ messages,
+
+ schema: [{
+ type: 'object',
+ properties: {
+ noTemplateLiterals: {
+ type: 'boolean',
+ },
+ },
+ additionalProperties: false,
+ }],
+ },
+
+ create(context) {
+ const checkRefsUsage = testReactVersion(context, '< 18.3.0'); // `this.refs` is writable in React 18.3.0 and later, see https://github.com/facebook/react/pull/28867
+ const detectTemplateLiterals = context.options[0] ? context.options[0].noTemplateLiterals : false;
+ /**
+ * Checks if we are using refs
+ * @param {ASTNode} node The AST node being checked.
+ * @returns {boolean} True if we are using refs, false if not.
+ */
+ function isRefsUsage(node) {
+ return !!(
+ (componentUtil.getParentES6Component(context, node) || componentUtil.getParentES5Component(context, node))
+ && node.object.type === 'ThisExpression'
+ && node.property.name === 'refs'
+ );
+ }
+
+ /**
+ * Checks if we are using a ref attribute
+ * @param {ASTNode} node The AST node being checked.
+ * @returns {boolean} True if we are using a ref attribute, false if not.
+ */
+ function isRefAttribute(node) {
+ return node.type === 'JSXAttribute'
+ && !!node.name
+ && node.name.name === 'ref';
+ }
+
+ /**
+ * Checks if a node contains a string value
+ * @param {ASTNode} node The AST node being checked.
+ * @returns {boolean} True if the node contains a string value, false if not.
+ */
+ function containsStringLiteral(node) {
+ return !!node.value
+ && node.value.type === 'Literal'
+ && typeof node.value.value === 'string';
+ }
+
+ /**
+ * Checks if a node contains a string value within a jsx expression
+ * @param {ASTNode} node The AST node being checked.
+ * @returns {boolean} True if the node contains a string value within a jsx expression, false if not.
+ */
+ function containsStringExpressionContainer(node) {
+ return !!node.value
+ && node.value.type === 'JSXExpressionContainer'
+ && node.value.expression
+ && ((node.value.expression.type === 'Literal' && typeof node.value.expression.value === 'string')
+ || (node.value.expression.type === 'TemplateLiteral' && detectTemplateLiterals));
+ }
+
+ return {
+ MemberExpression(node) {
+ if (checkRefsUsage && isRefsUsage(node)) {
+ report(context, messages.thisRefsDeprecated, 'thisRefsDeprecated', {
+ node,
+ });
+ }
+ },
+
+ JSXAttribute(node) {
+ if (
+ isRefAttribute(node)
+ && (containsStringLiteral(node) || containsStringExpressionContainer(node))
+ ) {
+ report(context, messages.stringInRefDeprecated, 'stringInRefDeprecated', {
+ node,
+ });
+ }
+ },
+ };
+ },
+};
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-this-in-sfc.d.ts b/node_modules/eslint-plugin-react/lib/rules/no-this-in-sfc.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..37e259395ee82fa3f82aaa17f0dd7752f9aa39b5
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-this-in-sfc.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=no-this-in-sfc.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-this-in-sfc.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/no-this-in-sfc.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..0dbc892aee85ac5426b3fb949ed0fa6c6769a16d
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-this-in-sfc.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"no-this-in-sfc.d.ts","sourceRoot":"","sources":["no-this-in-sfc.js"],"names":[],"mappings":"wBAkBW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-this-in-sfc.js b/node_modules/eslint-plugin-react/lib/rules/no-this-in-sfc.js
new file mode 100644
index 0000000000000000000000000000000000000000..c520abd31cf9255fc5c0285cbaa9d3cf5224dee8
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-this-in-sfc.js
@@ -0,0 +1,47 @@
+/**
+ * @fileoverview Report "this" being used in stateless functional components.
+ */
+
+'use strict';
+
+const Components = require('../util/Components');
+const docsUrl = require('../util/docsUrl');
+const report = require('../util/report');
+
+// ------------------------------------------------------------------------------
+// Rule Definition
+// ------------------------------------------------------------------------------
+
+const messages = {
+ noThisInSFC: 'Stateless functional components should not use `this`',
+};
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = {
+ meta: {
+ docs: {
+ description: 'Disallow `this` from being used in stateless functional components',
+ category: 'Possible Errors',
+ recommended: false,
+ url: docsUrl('no-this-in-sfc'),
+ },
+
+ messages,
+
+ schema: [],
+ },
+
+ create: Components.detect((context, components, utils) => ({
+ MemberExpression(node) {
+ if (node.object.type === 'ThisExpression') {
+ const component = components.get(utils.getParentStatelessComponent(node));
+ if (!component || (component.node && component.node.parent && component.node.parent.type === 'Property')) {
+ return;
+ }
+ report(context, messages.noThisInSFC, 'noThisInSFC', {
+ node,
+ });
+ }
+ },
+ })),
+};
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-typos.d.ts b/node_modules/eslint-plugin-react/lib/rules/no-typos.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..e7f262b03b914cba224cf9cdad86bbd8b660edcb
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-typos.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=no-typos.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-typos.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/no-typos.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..0bebb0383a12c784cf7306bb6df7874475821cfc
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-typos.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"no-typos.d.ts","sourceRoot":"","sources":["no-typos.js"],"names":[],"mappings":"wBA+BW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-typos.js b/node_modules/eslint-plugin-react/lib/rules/no-typos.js
new file mode 100644
index 0000000000000000000000000000000000000000..a598a8e1142c8f96ccb966ab7ddabe8dda09b6f4
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-typos.js
@@ -0,0 +1,260 @@
+/**
+ * @fileoverview Prevent common casing typos
+ */
+
+'use strict';
+
+const PROP_TYPES = Object.keys(require('prop-types'));
+const Components = require('../util/Components');
+const docsUrl = require('../util/docsUrl');
+const astUtil = require('../util/ast');
+const componentUtil = require('../util/componentUtil');
+const report = require('../util/report');
+const lifecycleMethods = require('../util/lifecycleMethods');
+
+// ------------------------------------------------------------------------------
+// Rule Definition
+// ------------------------------------------------------------------------------
+
+const STATIC_CLASS_PROPERTIES = ['propTypes', 'contextTypes', 'childContextTypes', 'defaultProps'];
+
+const messages = {
+ typoPropTypeChain: 'Typo in prop type chain qualifier: {{name}}',
+ typoPropType: 'Typo in declared prop type: {{name}}',
+ typoStaticClassProp: 'Typo in static class property declaration',
+ typoPropDeclaration: 'Typo in property declaration',
+ typoLifecycleMethod: 'Typo in component lifecycle method declaration: {{actual}} should be {{expected}}',
+ staticLifecycleMethod: 'Lifecycle method should be static: {{method}}',
+ noPropTypesBinding: '`\'prop-types\'` imported without a local `PropTypes` binding.',
+ noReactBinding: '`\'react\'` imported without a local `React` binding.',
+};
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = {
+ meta: {
+ docs: {
+ description: 'Disallow common typos',
+ category: 'Stylistic Issues',
+ recommended: false,
+ url: docsUrl('no-typos'),
+ },
+
+ messages,
+
+ schema: [],
+ },
+
+ create: Components.detect((context, components, utils) => {
+ let propTypesPackageName = null;
+ let reactPackageName = null;
+
+ function checkValidPropTypeQualifier(node) {
+ if (node.name !== 'isRequired') {
+ report(context, messages.typoPropTypeChain, 'typoPropTypeChain', {
+ node,
+ data: { name: node.name },
+ });
+ }
+ }
+
+ function checkValidPropType(node) {
+ if (node.name && !PROP_TYPES.some((propTypeName) => propTypeName === node.name)) {
+ report(context, messages.typoPropType, 'typoPropType', {
+ node,
+ data: { name: node.name },
+ });
+ }
+ }
+
+ function isPropTypesPackage(node) {
+ return (
+ node.type === 'Identifier'
+ && node.name === propTypesPackageName
+ ) || (
+ node.type === 'MemberExpression'
+ && node.property.name === 'PropTypes'
+ && node.object.name === reactPackageName
+ );
+ }
+
+ /* eslint-disable no-use-before-define */
+
+ function checkValidCallExpression(node) {
+ const callee = node.callee;
+ if (callee.type === 'MemberExpression' && callee.property.name === 'shape') {
+ checkValidPropObject(node.arguments[0]);
+ } else if (callee.type === 'MemberExpression' && callee.property.name === 'oneOfType') {
+ const args = node.arguments[0];
+ if (args && args.type === 'ArrayExpression') {
+ args.elements.forEach((el) => {
+ checkValidProp(el);
+ });
+ }
+ }
+ }
+
+ function checkValidProp(node) {
+ if ((!propTypesPackageName && !reactPackageName) || !node) {
+ return;
+ }
+
+ if (node.type === 'MemberExpression') {
+ if (
+ node.object.type === 'MemberExpression'
+ && isPropTypesPackage(node.object.object)
+ ) { // PropTypes.myProp.isRequired
+ checkValidPropType(node.object.property);
+ checkValidPropTypeQualifier(node.property);
+ } else if (
+ isPropTypesPackage(node.object)
+ && node.property.name !== 'isRequired'
+ ) { // PropTypes.myProp
+ checkValidPropType(node.property);
+ } else if (astUtil.isCallExpression(node.object)) {
+ checkValidPropTypeQualifier(node.property);
+ checkValidCallExpression(node.object);
+ }
+ } else if (astUtil.isCallExpression(node)) {
+ checkValidCallExpression(node);
+ }
+ }
+
+ /* eslint-enable no-use-before-define */
+
+ function checkValidPropObject(node) {
+ if (node && node.type === 'ObjectExpression') {
+ node.properties.forEach((prop) => checkValidProp(prop.value));
+ }
+ }
+
+ function reportErrorIfPropertyCasingTypo(propertyValue, propertyKey, isClassProperty) {
+ const propertyName = propertyKey.name;
+ if (propertyName === 'propTypes' || propertyName === 'contextTypes' || propertyName === 'childContextTypes') {
+ checkValidPropObject(propertyValue);
+ }
+ STATIC_CLASS_PROPERTIES.forEach((CLASS_PROP) => {
+ if (propertyName && CLASS_PROP.toLowerCase() === propertyName.toLowerCase() && CLASS_PROP !== propertyName) {
+ const messageId = isClassProperty
+ ? 'typoStaticClassProp'
+ : 'typoPropDeclaration';
+ report(context, messages[messageId], messageId, {
+ node: propertyKey,
+ });
+ }
+ });
+ }
+
+ function reportErrorIfLifecycleMethodCasingTypo(node) {
+ const key = node.key;
+ let nodeKeyName = key.name;
+ if (key.type === 'Literal') {
+ nodeKeyName = key.value;
+ }
+ if (key.type === 'PrivateName' || (node.computed && typeof nodeKeyName !== 'string')) {
+ return;
+ }
+
+ lifecycleMethods.static.forEach((method) => {
+ if (!node.static && nodeKeyName && nodeKeyName.toLowerCase() === method.toLowerCase()) {
+ report(context, messages.staticLifecycleMethod, 'staticLifecycleMethod', {
+ node,
+ data: {
+ method: nodeKeyName,
+ },
+ });
+ }
+ });
+
+ lifecycleMethods.instance.concat(lifecycleMethods.static).forEach((method) => {
+ if (nodeKeyName && method.toLowerCase() === nodeKeyName.toLowerCase() && method !== nodeKeyName) {
+ report(context, messages.typoLifecycleMethod, 'typoLifecycleMethod', {
+ node,
+ data: { actual: nodeKeyName, expected: method },
+ });
+ }
+ });
+ }
+
+ return {
+ ImportDeclaration(node) {
+ if (node.source && node.source.value === 'prop-types') { // import PropType from "prop-types"
+ if (node.specifiers.length > 0) {
+ propTypesPackageName = node.specifiers[0].local.name;
+ } else {
+ report(context, messages.noPropTypesBinding, 'noPropTypesBinding', {
+ node,
+ });
+ }
+ } else if (node.source && node.source.value === 'react') { // import { PropTypes } from "react"
+ if (node.specifiers.length > 0) {
+ reactPackageName = node.specifiers[0].local.name; // guard against accidental anonymous `import "react"`
+ } else {
+ report(context, messages.noReactBinding, 'noReactBinding', {
+ node,
+ });
+ }
+ if (node.specifiers.length >= 1) {
+ const propTypesSpecifier = node.specifiers.find((specifier) => (
+ specifier.imported
+ && specifier.imported.name === 'PropTypes'
+ ));
+ if (propTypesSpecifier) {
+ propTypesPackageName = propTypesSpecifier.local.name;
+ }
+ }
+ }
+ },
+
+ 'ClassProperty, PropertyDefinition'(node) {
+ if (!node.static || !componentUtil.isES6Component(node.parent.parent, context)) {
+ return;
+ }
+
+ reportErrorIfPropertyCasingTypo(node.value, node.key, true);
+ },
+
+ MemberExpression(node) {
+ const propertyName = node.property.name;
+
+ if (
+ !propertyName
+ || STATIC_CLASS_PROPERTIES.map((prop) => prop.toLocaleLowerCase()).indexOf(propertyName.toLowerCase()) === -1
+ ) {
+ return;
+ }
+
+ const relatedComponent = utils.getRelatedComponent(node);
+
+ if (
+ relatedComponent
+ && (componentUtil.isES6Component(relatedComponent.node, context) || (
+ relatedComponent.node.type !== 'ClassDeclaration' && utils.isReturningJSX(relatedComponent.node)))
+ && (node.parent && node.parent.type === 'AssignmentExpression' && node.parent.right)
+ ) {
+ reportErrorIfPropertyCasingTypo(node.parent.right, node.property, true);
+ }
+ },
+
+ MethodDefinition(node) {
+ if (!componentUtil.isES6Component(node.parent.parent, context)) {
+ return;
+ }
+
+ reportErrorIfLifecycleMethodCasingTypo(node);
+ },
+
+ ObjectExpression(node) {
+ const component = componentUtil.isES5Component(node, context) && components.get(node);
+
+ if (!component) {
+ return;
+ }
+
+ node.properties.filter((property) => property.type !== 'SpreadElement').forEach((property) => {
+ reportErrorIfPropertyCasingTypo(property.value, property.key, false);
+ reportErrorIfLifecycleMethodCasingTypo(property);
+ });
+ },
+ };
+ }),
+};
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-unescaped-entities.d.ts b/node_modules/eslint-plugin-react/lib/rules/no-unescaped-entities.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..baaf17d86608bb9a00d51fe4ca8d5887d0d106a1
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-unescaped-entities.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=no-unescaped-entities.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-unescaped-entities.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/no-unescaped-entities.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..130436b918c7bbf80210be09f4fe88023514ab1d
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-unescaped-entities.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"no-unescaped-entities.d.ts","sourceRoot":"","sources":["no-unescaped-entities.js"],"names":[],"mappings":"wBAwCW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-unescaped-entities.js b/node_modules/eslint-plugin-react/lib/rules/no-unescaped-entities.js
new file mode 100644
index 0000000000000000000000000000000000000000..3ec2cb23b6b2984ac9a236bd32db3e4b91eec6ec
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-unescaped-entities.js
@@ -0,0 +1,157 @@
+/**
+ * @fileoverview HTML special characters should be escaped.
+ * @author Patrick Hayes
+ */
+
+'use strict';
+
+const docsUrl = require('../util/docsUrl');
+const getSourceCode = require('../util/eslint').getSourceCode;
+const jsxUtil = require('../util/jsx');
+const report = require('../util/report');
+const getMessageData = require('../util/message');
+
+// ------------------------------------------------------------------------------
+// Rule Definition
+// ------------------------------------------------------------------------------
+
+// NOTE: '<' and '{' are also problematic characters, but they do not need
+// to be included here because it is a syntax error when these characters are
+// included accidentally.
+const DEFAULTS = [{
+ char: '>',
+ alternatives: ['>'],
+}, {
+ char: '"',
+ alternatives: ['"', '“', '"', '”'],
+}, {
+ char: '\'',
+ alternatives: [''', '‘', ''', '’'],
+}, {
+ char: '}',
+ alternatives: ['}'],
+}];
+
+const messages = {
+ unescapedEntity: 'HTML entity, `{{entity}}` , must be escaped.',
+ unescapedEntityAlts: '`{{entity}}` can be escaped with {{alts}}.',
+ replaceWithAlt: 'Replace with `{{alt}}`.',
+};
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = {
+ meta: {
+ hasSuggestions: true,
+ docs: {
+ description: 'Disallow unescaped HTML entities from appearing in markup',
+ category: 'Possible Errors',
+ recommended: true,
+ url: docsUrl('no-unescaped-entities'),
+ },
+
+ messages,
+
+ schema: [{
+ type: 'object',
+ properties: {
+ forbid: {
+ type: 'array',
+ items: {
+ anyOf: [{
+ type: 'string',
+ }, {
+ type: 'object',
+ properties: {
+ char: {
+ type: 'string',
+ },
+ alternatives: {
+ type: 'array',
+ uniqueItems: true,
+ items: {
+ type: 'string',
+ },
+ },
+ },
+ }],
+ },
+ },
+ },
+ additionalProperties: false,
+ }],
+ },
+
+ create(context) {
+ function reportInvalidEntity(node) {
+ const configuration = context.options[0] || {};
+ const entities = configuration.forbid || DEFAULTS;
+
+ // HTML entities are already escaped in node.value (as well as node.raw),
+ // so pull the raw text from getSourceCode(context)
+ for (let i = node.loc.start.line; i <= node.loc.end.line; i++) {
+ let rawLine = getSourceCode(context).lines[i - 1];
+ let start = 0;
+ let end = rawLine.length;
+ if (i === node.loc.start.line) {
+ start = node.loc.start.column;
+ }
+ if (i === node.loc.end.line) {
+ end = node.loc.end.column;
+ }
+ rawLine = rawLine.slice(start, end);
+ for (let j = 0; j < entities.length; j++) {
+ for (let index = 0; index < rawLine.length; index++) {
+ const c = rawLine[index];
+ if (typeof entities[j] === 'string') {
+ if (c === entities[j]) {
+ report(context, messages.unescapedEntity, 'unescapedEntity', {
+ node,
+ loc: { line: i, column: start + index },
+ data: {
+ entity: entities[j],
+ },
+ });
+ }
+ } else if (c === entities[j].char) {
+ report(context, messages.unescapedEntityAlts, 'unescapedEntityAlts', {
+ node,
+ loc: { line: i, column: start + index },
+ data: {
+ entity: entities[j].char,
+ alts: entities[j].alternatives.map((alt) => `\`${alt}\``).join(', '),
+ },
+ suggest: entities[j].alternatives.map((alt) => Object.assign(
+ getMessageData('replaceWithAlt', messages.replaceWithAlt),
+ {
+ data: { alt },
+ fix(fixer) {
+ const lineToChange = i - node.loc.start.line;
+
+ const newText = node.raw.split('\n').map((line, idx) => {
+ if (idx === lineToChange) {
+ return line.slice(0, index) + alt + line.slice(index + 1);
+ }
+
+ return line;
+ }).join('\n');
+
+ return fixer.replaceText(node, newText);
+ },
+ }
+ )),
+ });
+ }
+ }
+ }
+ }
+ }
+
+ return {
+ 'Literal, JSXText'(node) {
+ if (jsxUtil.isJSX(node.parent)) {
+ reportInvalidEntity(node);
+ }
+ },
+ };
+ },
+};
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-unknown-property.d.ts b/node_modules/eslint-plugin-react/lib/rules/no-unknown-property.d.ts
new file mode 100644
index 0000000000000000000000000000000000000000..49a219c3ddd4da24fe1c2918e94d572cc3cfc0cb
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-unknown-property.d.ts
@@ -0,0 +1,3 @@
+declare const _exports: import('eslint').Rule.RuleModule;
+export = _exports;
+//# sourceMappingURL=no-unknown-property.d.ts.map
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-unknown-property.d.ts.map b/node_modules/eslint-plugin-react/lib/rules/no-unknown-property.d.ts.map
new file mode 100644
index 0000000000000000000000000000000000000000..e1e1e49a9fa3ca81b63977bc1c49f449d0fe83cf
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-unknown-property.d.ts.map
@@ -0,0 +1 @@
+{"version":3,"file":"no-unknown-property.d.ts","sourceRoot":"","sources":["no-unknown-property.js"],"names":[],"mappings":"wBAshBW,OAAO,QAAQ,EAAE,IAAI,CAAC,UAAU"}
\ No newline at end of file
diff --git a/node_modules/eslint-plugin-react/lib/rules/no-unknown-property.js b/node_modules/eslint-plugin-react/lib/rules/no-unknown-property.js
new file mode 100644
index 0000000000000000000000000000000000000000..d702cc43039f0fdce6dae36d690079d67fcf8be2
--- /dev/null
+++ b/node_modules/eslint-plugin-react/lib/rules/no-unknown-property.js
@@ -0,0 +1,671 @@
+/**
+ * @fileoverview Prevent usage of unknown DOM property
+ * @author Yannick Croissant
+ */
+
+'use strict';
+
+const has = require('hasown');
+const docsUrl = require('../util/docsUrl');
+const getText = require('../util/eslint').getText;
+const testReactVersion = require('../util/version').testReactVersion;
+const report = require('../util/report');
+
+// ------------------------------------------------------------------------------
+// Constants
+// ------------------------------------------------------------------------------
+
+const DEFAULTS = {
+ ignore: [],
+ requireDataLowercase: false,
+};
+
+const DOM_ATTRIBUTE_NAMES = {
+ 'accept-charset': 'acceptCharset',
+ class: 'className',
+ 'http-equiv': 'httpEquiv',
+ crossorigin: 'crossOrigin',
+ for: 'htmlFor',
+ nomodule: 'noModule',
+};
+
+const ATTRIBUTE_TAGS_MAP = {
+ abbr: ['th', 'td'],
+ charset: ['meta'],
+ checked: ['input'],
+ // image is required for SVG support, all other tags are HTML.
+ crossOrigin: ['script', 'img', 'video', 'audio', 'link', 'image'],
+ displaystyle: ['math'],
+ // https://html.spec.whatwg.org/multipage/links.html#downloading-resources
+ download: ['a', 'area'],
+ fill: [ // https://developer.mozilla.org/en-US/docs/Web/SVG/Attribute/fill
+ // Fill color
+ 'altGlyph',
+ 'circle',
+ 'ellipse',
+ 'g',
+ 'line',
+ 'marker',
+ 'mask',
+ 'path',
+ 'polygon',
+ 'polyline',
+ 'rect',
+ 'svg',
+ 'symbol',
+ 'text',
+ 'textPath',
+ 'tref',
+ 'tspan',
+ 'use',
+ // Animation final state
+ 'animate',
+ 'animateColor',
+ 'animateMotion',
+ 'animateTransform',
+ 'set',
+ ],
+ focusable: ['svg'],
+ imageSizes: ['link'],
+ imageSrcSet: ['link'],
+ property: ['meta'],
+ viewBox: ['marker', 'pattern', 'svg', 'symbol', 'view'],
+ as: ['link'],
+ align: ['applet', 'caption', 'col', 'colgroup', 'hr', 'iframe', 'img', 'table', 'tbody', 'td', 'tfoot', 'th', 'thead', 'tr'], // deprecated, but known
+ valign: ['tr', 'td', 'th', 'thead', 'tbody', 'tfoot', 'colgroup', 'col'], // deprecated, but known
+ noModule: ['script'],
+ // Media events allowed only on audio and video tags, see https://github.com/facebook/react/blob/256aefbea1449869620fb26f6ec695536ab453f5/CHANGELOG.md#notable-enhancements
+ onAbort: ['audio', 'video'],
+ onCancel: ['dialog'],
+ onCanPlay: ['audio', 'video'],
+ onCanPlayThrough: ['audio', 'video'],
+ onClose: ['dialog'],
+ onDurationChange: ['audio', 'video'],
+ onEmptied: ['audio', 'video'],
+ onEncrypted: ['audio', 'video'],
+ onEnded: ['audio', 'video'],
+ onError: ['audio', 'video', 'img', 'link', 'source', 'script', 'picture', 'iframe'],
+ onLoad: ['script', 'img', 'link', 'picture', 'iframe', 'object', 'source'],
+ onLoadedData: ['audio', 'video'],
+ onLoadedMetadata: ['audio', 'video'],
+ onLoadStart: ['audio', 'video'],
+ onPause: ['audio', 'video'],
+ onPlay: ['audio', 'video'],
+ onPlaying: ['audio', 'video'],
+ onProgress: ['audio', 'video'],
+ onRateChange: ['audio', 'video'],
+ onResize: ['audio', 'video'],
+ onSeeked: ['audio', 'video'],
+ onSeeking: ['audio', 'video'],
+ onStalled: ['audio', 'video'],
+ onSuspend: ['audio', 'video'],
+ onTimeUpdate: ['audio', 'video'],
+ onVolumeChange: ['audio', 'video'],
+ onWaiting: ['audio', 'video'],
+ autoPictureInPicture: ['video'],
+ controls: ['audio', 'video'],
+ controlsList: ['audio', 'video'],
+ disablePictureInPicture: ['video'],
+ disableRemotePlayback: ['audio', 'video'],
+ loop: ['audio', 'video'],
+ muted: ['audio', 'video'],
+ playsInline: ['video'],
+ allowFullScreen: ['iframe', 'video'],
+ webkitAllowFullScreen: ['iframe', 'video'],
+ mozAllowFullScreen: ['iframe', 'video'],
+ poster: ['video'],
+ preload: ['audio', 'video'],
+ scrolling: ['iframe'],
+ returnValue: ['dialog'],
+ webkitDirectory: ['input'],
+ shadowrootmode: ['template'],
+ shadowrootclonable: ['template'],
+ shadowrootdelegatesfocus: ['template'],
+ shadowrootserializable: ['template'],
+ 'transform-origin': ['rect'],
+};
+
+const SVGDOM_ATTRIBUTE_NAMES = {
+ 'accent-height': 'accentHeight',
+ 'alignment-baseline': 'alignmentBaseline',
+ 'arabic-form': 'arabicForm',
+ 'baseline-shift': 'baselineShift',
+ 'cap-height': 'capHeight',
+ 'clip-path': 'clipPath',
+ 'clip-rule': 'clipRule',
+ 'color-interpolation': 'colorInterpolation',
+ 'color-interpolation-filters': 'colorInterpolationFilters',
+ 'color-profile': 'colorProfile',
+ 'color-rendering': 'colorRendering',
+ 'dominant-baseline': 'dominantBaseline',
+ 'enable-background': 'enableBackground',
+ 'fill-opacity': 'fillOpacity',
+ 'fill-rule': 'fillRule',
+ 'flood-color': 'floodColor',
+ 'flood-opacity': 'floodOpacity',
+ 'font-family': 'fontFamily',
+ 'font-size': 'fontSize',
+ 'font-size-adjust': 'fontSizeAdjust',
+ 'font-stretch': 'fontStretch',
+ 'font-style': 'fontStyle',
+ 'font-variant': 'fontVariant',
+ 'font-weight': 'fontWeight',
+ 'glyph-name': 'glyphName',
+ 'glyph-orientation-horizontal': 'glyphOrientationHorizontal',
+ 'glyph-orientation-vertical': 'glyphOrientationVertical',
+ 'horiz-adv-x': 'horizAdvX',
+ 'horiz-origin-x': 'horizOriginX',
+ 'image-rendering': 'imageRendering',
+ 'letter-spacing': 'letterSpacing',
+ 'lighting-color': 'lightingColor',
+ 'marker-end': 'markerEnd',
+ 'marker-mid': 'markerMid',
+ 'marker-start': 'markerStart',
+ 'overline-position': 'overlinePosition',
+ 'overline-thickness': 'overlineThickness',
+ 'paint-order': 'paintOrder',
+ 'panose-1': 'panose1',
+ 'pointer-events': 'pointerEvents',
+ 'rendering-intent': 'renderingIntent',
+ 'shape-rendering': 'shapeRendering',
+ 'stop-color': 'stopColor',
+ 'stop-opacity': 'stopOpacity',
+ 'strikethrough-position': 'strikethroughPosition',
+ 'strikethrough-thickness': 'strikethroughThickness',
+ 'stroke-dasharray': 'strokeDasharray',
+ 'stroke-dashoffset': 'strokeDashoffset',
+ 'stroke-linecap': 'strokeLinecap',
+ 'stroke-linejoin': 'strokeLinejoin',
+ 'stroke-miterlimit': 'strokeMiterlimit',
+ 'stroke-opacity': 'strokeOpacity',
+ 'stroke-width': 'strokeWidth',
+ 'text-anchor': 'textAnchor',
+ 'text-decoration': 'textDecoration',
+ 'text-rendering': 'textRendering',
+ 'underline-position': 'underlinePosition',
+ 'underline-thickness': 'underlineThickness',
+ 'unicode-bidi': 'unicodeBidi',
+ 'unicode-range': 'unicodeRange',
+ 'units-per-em': 'unitsPerEm',
+ 'v-alphabetic': 'vAlphabetic',
+ 'v-hanging': 'vHanging',
+ 'v-ideographic': 'vIdeographic',
+ 'v-mathematical': 'vMathematical',
+ 'vector-effect': 'vectorEffect',
+ 'vert-adv-y': 'vertAdvY',
+ 'vert-origin-x': 'vertOriginX',
+ 'vert-origin-y': 'vertOriginY',
+ 'word-spacing': 'wordSpacing',
+ 'writing-mode': 'writingMode',
+ 'x-height': 'xHeight',
+ 'xlink:actuate': 'xlinkActuate',
+ 'xlink:arcrole': 'xlinkArcrole',
+ 'xlink:href': 'xlinkHref',
+ 'xlink:role': 'xlinkRole',
+ 'xlink:show': 'xlinkShow',
+ 'xlink:title': 'xlinkTitle',
+ 'xlink:type': 'xlinkType',
+ 'xml:base': 'xmlBase',
+ 'xml:lang': 'xmlLang',
+ 'xml:space': 'xmlSpace',
+};
+
+const DOM_PROPERTY_NAMES_ONE_WORD = [
+ // Global attributes - can be used on any HTML/DOM element
+ // See https://developer.mozilla.org/en-US/docs/Web/HTML/Global_attributes
+ 'dir', 'draggable', 'hidden', 'id', 'lang', 'nonce', 'part', 'slot', 'style', 'title', 'translate', 'inert',
+ // Element specific attributes
+ // See https://developer.mozilla.org/en-US/docs/Web/HTML/Attributes (includes global attributes too)
+ // To be considered if these should be added also to ATTRIBUTE_TAGS_MAP
+ 'accept', 'action', 'allow', 'alt', 'as', 'async', 'buffered', 'capture', 'challenge', 'cite', 'code', 'cols',
+ 'content', 'coords', 'csp', 'data', 'decoding', 'default', 'defer', 'disabled', 'form',
+ 'headers', 'height', 'high', 'href', 'icon', 'importance', 'integrity', 'kind', 'label',
+ 'language', 'loading', 'list', 'loop', 'low', 'manifest', 'max', 'media', 'method', 'min', 'multiple', 'muted',
+ 'name', 'open', 'optimum', 'pattern', 'ping', 'placeholder', 'poster', 'preload', 'profile',
+ 'rel', 'required', 'reversed', 'role', 'rows', 'sandbox', 'scope', 'seamless', 'selected', 'shape', 'size', 'sizes',
+ 'span', 'src', 'start', 'step', 'summary', 'target', 'type', 'value', 'width', 'wmode', 'wrap',
+ // SVG attributes
+ // See https://developer.mozilla.org/en-US/docs/Web/SVG/Attribute
+ 'accumulate', 'additive', 'alphabetic', 'amplitude', 'ascent', 'azimuth', 'bbox', 'begin',
+ 'bias', 'by', 'clip', 'color', 'cursor', 'cx', 'cy', 'd', 'decelerate', 'descent', 'direction',
+ 'display', 'divisor', 'dur', 'dx', 'dy', 'elevation', 'end', 'exponent', 'fill', 'filter',
+ 'format', 'from', 'fr', 'fx', 'fy', 'g1', 'g2', 'hanging', 'height', 'hreflang', 'ideographic',
+ 'in', 'in2', 'intercept', 'k', 'k1', 'k2', 'k3', 'k4', 'kerning', 'local', 'mask', 'mode',
+ 'offset', 'opacity', 'operator', 'order', 'orient', 'orientation', 'origin', 'overflow', 'path',
+ 'ping', 'points', 'r', 'radius', 'rel', 'restart', 'result', 'rotate', 'rx', 'ry', 'scale',
+ 'seed', 'slope', 'spacing', 'speed', 'stemh', 'stemv', 'string', 'stroke', 'to', 'transform',
+ 'u1', 'u2', 'unicode', 'values', 'version', 'visibility', 'widths', 'x', 'x1', 'x2', 'xmlns',
+ 'y', 'y1', 'y2', 'z',
+ // OpenGraph meta tag attributes
+ 'property',
+ // React specific attributes
+ 'ref', 'key', 'children',
+ // Non-standard
+ 'results', 'security',
+ // Video specific
+ 'controls',
+ // popovers
+ 'popover', 'popovertarget', 'popovertargetaction',
+];
+
+const DOM_PROPERTY_NAMES_TWO_WORDS = [
+ // Global attributes - can be used on any HTML/DOM element
+ // See https://developer.mozilla.org/en-US/docs/Web/HTML/Global_attributes
+ 'accessKey', 'autoCapitalize', 'autoFocus', 'contentEditable', 'enterKeyHint', 'exportParts',
+ 'inputMode', 'itemID', 'itemRef', 'itemProp', 'itemScope', 'itemType', 'spellCheck', 'tabIndex',
+ // Element specific attributes
+ // See https://developer.mozilla.org/en-US/docs/Web/HTML/Attributes (includes global attributes too)
+ // To be considered if these should be added also to ATTRIBUTE_TAGS_MAP
+ 'acceptCharset', 'autoComplete', 'autoPlay', 'border', 'cellPadding', 'cellSpacing', 'classID', 'codeBase',
+ 'colSpan', 'contextMenu', 'dateTime', 'encType', 'formAction', 'formEncType', 'formMethod', 'formNoValidate', 'formTarget',
+ 'frameBorder', 'hrefLang', 'httpEquiv', 'imageSizes', 'imageSrcSet', 'isMap', 'keyParams', 'keyType', 'marginHeight', 'marginWidth',
+ 'maxLength', 'mediaGroup', 'minLength', 'noValidate', 'onAnimationEnd', 'onAnimationIteration', 'onAnimationStart',
+ 'onBlur', 'onChange', 'onClick', 'onContextMenu', 'onCopy', 'onCompositionEnd', 'onCompositionStart',
+ 'onCompositionUpdate', 'onCut', 'onDoubleClick', 'onDrag', 'onDragEnd', 'onDragEnter', 'onDragExit', 'onDragLeave',
+ 'onError', 'onFocus', 'onInput', 'onKeyDown', 'onKeyPress', 'onKeyUp', 'onLoad', 'onWheel', 'onDragOver',
+ 'onDragStart', 'onDrop', 'onMouseDown', 'onMouseEnter', 'onMouseLeave', 'onMouseMove', 'onMouseOut', 'onMouseOver',
+ 'onMouseUp', 'onPaste', 'onScroll', 'onSelect', 'onSubmit', 'onBeforeToggle', 'onToggle', 'onTransitionEnd', 'radioGroup',
+ 'readOnly', 'referrerPolicy', 'rowSpan', 'srcDoc', 'srcLang', 'srcSet', 'useMap', 'fetchPriority',
+ // SVG attributes
+ // See https://developer.mozilla.org/en-US/docs/Web/SVG/Attribute
+ 'crossOrigin', 'accentHeight', 'alignmentBaseline', 'arabicForm', 'attributeName',
+ 'attributeType', 'baseFrequency', 'baselineShift', 'baseProfile', 'calcMode', 'capHeight',
+ 'clipPathUnits', 'clipPath', 'clipRule', 'colorInterpolation', 'colorInterpolationFilters',
+ 'colorProfile', 'colorRendering', 'contentScriptType', 'contentStyleType', 'diffuseConstant',
+ 'dominantBaseline', 'edgeMode', 'enableBackground', 'fillOpacity', 'fillRule', 'filterRes',
+ 'filterUnits', 'floodColor', 'floodOpacity', 'fontFamily', 'fontSize', 'fontSizeAdjust',
+ 'fontStretch', 'fontStyle', 'fontVariant', 'fontWeight', 'glyphName',
+ 'glyphOrientationHorizontal', 'glyphOrientationVertical', 'glyphRef', 'gradientTransform',
+ 'gradientUnits', 'horizAdvX', 'horizOriginX', 'imageRendering', 'kernelMatrix',
+ 'kernelUnitLength', 'keyPoints', 'keySplines', 'keyTimes', 'lengthAdjust', 'letterSpacing',
+ 'lightingColor', 'limitingConeAngle', 'markerEnd', 'markerMid', 'markerStart', 'markerHeight',
+ 'markerUnits', 'markerWidth', 'maskContentUnits', 'maskUnits', 'mathematical', 'numOctaves',
+ 'overlinePosition', 'overlineThickness', 'panose1', 'paintOrder', 'pathLength',
+ 'patternContentUnits', 'patternTransform', 'patternUnits', 'pointerEvents', 'pointsAtX',
+ 'pointsAtY', 'pointsAtZ', 'preserveAlpha', 'preserveAspectRatio', 'primitiveUnits',
+ 'referrerPolicy', 'refX', 'refY', 'rendering-intent', 'repeatCount', 'repeatDur',
+ 'requiredExtensions', 'requiredFeatures', 'shapeRendering', 'specularConstant',
+ 'specularExponent', 'spreadMethod', 'startOffset', 'stdDeviation', 'stitchTiles', 'stopColor',
+ 'stopOpacity', 'strikethroughPosition', 'strikethroughThickness', 'strokeDasharray',
+ 'strokeDashoffset', 'strokeLinecap', 'strokeLinejoin', 'strokeMiterlimit', 'strokeOpacity',
+ 'strokeWidth', 'surfaceScale', 'systemLanguage', 'tableValues', 'targetX', 'targetY',
+ 'textAnchor', 'textDecoration', 'textRendering', 'textLength', 'transformOrigin',
+ 'underlinePosition', 'underlineThickness', 'unicodeBidi', 'unicodeRange', 'unitsPerEm',
+ 'vAlphabetic', 'vHanging', 'vIdeographic', 'vMathematical', 'vectorEffect', 'vertAdvY',
+ 'vertOriginX', 'vertOriginY', 'viewBox', 'viewTarget', 'wordSpacing', 'writingMode', 'xHeight',
+ 'xChannelSelector', 'xlinkActuate', 'xlinkArcrole', 'xlinkHref', 'xlinkRole', 'xlinkShow',
+ 'xlinkTitle', 'xlinkType', 'xmlBase', 'xmlLang', 'xmlnsXlink', 'xmlSpace', 'yChannelSelector',
+ 'zoomAndPan',
+ // Safari/Apple specific, no listing available
+ 'autoCorrect', // https://stackoverflow.com/questions/47985384/html-autocorrect-for-text-input-is-not-working
+ 'autoSave', // https://stackoverflow.com/questions/25456396/what-is-autosave-attribute-supposed-to-do-how-do-i-use-it
+ // React specific attributes https://reactjs.org/docs/dom-elements.html#differences-in-attributes
+ 'className', 'dangerouslySetInnerHTML', 'defaultValue', 'defaultChecked', 'htmlFor',
+ // Events' capture events
+ 'onBeforeInput', 'onChange',
+ 'onInvalid', 'onReset', 'onTouchCancel', 'onTouchEnd', 'onTouchMove', 'onTouchStart', 'suppressContentEditableWarning', 'suppressHydrationWarning',
+ 'onAbort', 'onCanPlay', 'onCanPlayThrough', 'onDurationChange', 'onEmptied', 'onEncrypted', 'onEnded',
+ 'onLoadedData', 'onLoadedMetadata', 'onLoadStart', 'onPause', 'onPlay', 'onPlaying', 'onProgress', 'onRateChange', 'onResize',
+ 'onSeeked', 'onSeeking', 'onStalled', 'onSuspend', 'onTimeUpdate', 'onVolumeChange', 'onWaiting',
+ 'onCopyCapture', 'onCutCapture', 'onPasteCapture', 'onCompositionEndCapture', 'onCompositionStartCapture', 'onCompositionUpdateCapture',
+ 'onFocusCapture', 'onBlurCapture', 'onChangeCapture', 'onBeforeInputCapture', 'onInputCapture', 'onResetCapture', 'onSubmitCapture',
+ 'onInvalidCapture', 'onLoadCapture', 'onErrorCapture', 'onKeyDownCapture', 'onKeyPressCapture', 'onKeyUpCapture',
+ 'onAbortCapture', 'onCanPlayCapture', 'onCanPlayThroughCapture', 'onDurationChangeCapture', 'onEmptiedCapture', 'onEncryptedCapture',
+ 'onEndedCapture', 'onLoadedDataCapture', 'onLoadedMetadataCapture', 'onLoadStartCapture', 'onPauseCapture', 'onPlayCapture',
+ 'onPlayingCapture', 'onProgressCapture', 'onRateChangeCapture', 'onSeekedCapture', 'onSeekingCapture', 'onStalledCapture', 'onSuspendCapture',
+ 'onTimeUpdateCapture', 'onVolumeChangeCapture', 'onWaitingCapture', 'onSelectCapture', 'onTouchCancelCapture', 'onTouchEndCapture',
+ 'onTouchMoveCapture', 'onTouchStartCapture', 'onScrollCapture', 'onWheelCapture', 'onAnimationEndCapture', 'onAnimationIteration',
+ 'onAnimationStartCapture', 'onTransitionEndCapture',
+ 'onAuxClick', 'onAuxClickCapture', 'onClickCapture', 'onContextMenuCapture', 'onDoubleClickCapture',
+ 'onDragCapture', 'onDragEndCapture', 'onDragEnterCapture', 'onDragExitCapture', 'onDragLeaveCapture',
+ 'onDragOverCapture', 'onDragStartCapture', 'onDropCapture', 'onMouseDown', 'onMouseDownCapture',
+ 'onMouseMoveCapture', 'onMouseOutCapture', 'onMouseOverCapture', 'onMouseUpCapture',
+ // Video specific
+ 'autoPictureInPicture', 'controlsList', 'disablePictureInPicture', 'disableRemotePlayback',
+ // popovers
+ 'popoverTarget', 'popoverTargetAction',
+];
+
+const DOM_PROPERTIES_IGNORE_CASE = ['charset', 'allowFullScreen', 'webkitAllowFullScreen', 'mozAllowFullScreen', 'webkitDirectory', 'popoverTarget', 'popoverTargetAction'];
+
+const ARIA_PROPERTIES = [
+ // See https://developer.mozilla.org/en-US/docs/Web/Accessibility/ARIA/Attributes
+ // Global attributes
+ 'aria-atomic', 'aria-braillelabel', 'aria-brailleroledescription', 'aria-busy', 'aria-controls', 'aria-current',
+ 'aria-describedby', 'aria-description', 'aria-details',
+ 'aria-disabled', 'aria-dropeffect', 'aria-errormessage', 'aria-flowto', 'aria-grabbed', 'aria-haspopup',
+ 'aria-hidden', 'aria-invalid', 'aria-keyshortcuts', 'aria-label', 'aria-labelledby', 'aria-live',
+ 'aria-owns', 'aria-relevant', 'aria-roledescription',
+ // Widget attributes
+ 'aria-autocomplete', 'aria-checked', 'aria-expanded', 'aria-level', 'aria-modal', 'aria-multiline', 'aria-multiselectable',
+ 'aria-orientation', 'aria-placeholder', 'aria-pressed', 'aria-readonly', 'aria-required', 'aria-selected',
+ 'aria-sort', 'aria-valuemax', 'aria-valuemin', 'aria-valuenow', 'aria-valuetext',
+ // Relationship attributes
+ 'aria-activedescendant', 'aria-colcount', 'aria-colindex', 'aria-colindextext', 'aria-colspan',
+ 'aria-posinset', 'aria-rowcount', 'aria-rowindex', 'aria-rowindextext', 'aria-rowspan', 'aria-setsize',
+];
+
+const REACT_ON_PROPS = [
+ 'onGotPointerCapture',
+ 'onGotPointerCaptureCapture',
+ 'onLostPointerCapture',
+ 'onLostPointerCapture',
+ 'onLostPointerCaptureCapture',
+ 'onPointerCancel',
+ 'onPointerCancelCapture',
+ 'onPointerDown',
+ 'onPointerDownCapture',
+ 'onPointerEnter',
+ 'onPointerEnterCapture',
+ 'onPointerLeave',
+ 'onPointerLeaveCapture',
+ 'onPointerMove',
+ 'onPointerMoveCapture',
+ 'onPointerOut',
+ 'onPointerOutCapture',
+ 'onPointerOver',
+ 'onPointerOverCapture',
+ 'onPointerUp',
+ 'onPointerUpCapture',
+];
+
+function getDOMPropertyNames(context) {
+ return [].concat(
+ DOM_PROPERTY_NAMES_TWO_WORDS,
+ DOM_PROPERTY_NAMES_ONE_WORD,
+
+ testReactVersion(context, '>= 16.1.0') ? [].concat(
+ testReactVersion(context, '>= 16.4.0') ? [].concat(
+ // these were added in React v16.4.0, see https://reactjs.org/blog/2018/05/23/react-v-16-4.html and https://github.com/facebook/react/pull/12507
+ REACT_ON_PROPS,
+ testReactVersion(context, '>= 19') ? [
+ // precedence was added in React v19, see https://react.dev/blog/2024/04/25/react-19#support-for-stylesheets
+ 'precedence',
+ ] : []
+ ) : []
+ ) : [
+ // this was removed in React v16.1+, see https://github.com/facebook/react/pull/10823
+ 'allowTransparency',
+ ]
+ );
+}
+
+// ------------------------------------------------------------------------------
+// Helpers
+// ------------------------------------------------------------------------------
+
+/**
+ * Checks if a node's parent is a JSX tag that is written with lowercase letters,
+ * and is not a custom web component. Custom web components have a hyphen in tag name,
+ * or have an `is="some-elem"` attribute.
+ *
+ * Note: does not check if a tag's parent against a list of standard HTML/DOM tags. For example,
+ * a ``'s child would return `true` because "fake" is written only with lowercase letters
+ * without a hyphen and does not have a `is="some-elem"` attribute.
+ *
+ * @param {Object} childNode - JSX element being tested.
+ * @returns {boolean} Whether or not the node name match the JSX tag convention.
+ */
+function isValidHTMLTagInJSX(childNode) {
+ const tagConvention = /^[a-z][^-]*$/;
+ if (tagConvention.test(childNode.parent.name.name)) {
+ return !childNode.parent.attributes.some((attrNode) => (
+ attrNode.type === 'JSXAttribute'
+ && attrNode.name.type === 'JSXIdentifier'
+ && attrNode.name.name === 'is'
+ // To learn more about custom web components and `is` attribute,
+ // see https://html.spec.whatwg.org/multipage/custom-elements.html#custom-elements-customized-builtin-example
+
+ ));
+ }
+ return false;
+}
+
+/**
+ * Checks if the attribute name is included in the attributes that are excluded
+ * from the camel casing.
+ *
+ * // returns 'charSet'
+ * @example normalizeAttributeCase('charset')
+ *
+ * Note - these exclusions are not made by React core team, but `eslint-plugin-react` community.
+ *
+ * @param {string} name - Attribute name to be normalized
+ * @returns {string} Result
+ */
+function normalizeAttributeCase(name) {
+ return DOM_PROPERTIES_IGNORE_CASE.find((element) => element.toLowerCase() === name.toLowerCase()) || name;
+}
+
+/**
+ * Checks if an attribute name is a valid `data-*` attribute:
+ * if the name starts with "data-" and has alphanumeric words (browsers require lowercase, but React and TS lowercase them),
+ * not start with any casing of "xml", and separated by hyphens (-) (which is also called "kebab case" or "dash case"),
+ * then the attribute is a valid data attribute.
+ *
+ * @param {string} name - Attribute name to be tested
+ * @returns {boolean} Result
+ */
+function isValidDataAttribute(name) {
+ return !/^data-xml/i.test(name) && /^data-[^:]*$/.test(name);
+}
+
+/**
+ * Checks if an attribute name has at least one uppercase characters
+ *
+ * @param {string} name
+ * @returns {boolean} Result
+ */
+function hasUpperCaseCharacter(name) {
+ return name.toLowerCase() !== name;
+}
+
+/**
+ * Checks if an attribute name is a standard aria attribute by compering it to a list
+ * of standard aria property names
+ *
+ * @param {string} name - Attribute name to be tested
+ * @returns {boolean} Result
+ */
+
+function isValidAriaAttribute(name) {
+ return ARIA_PROPERTIES.some((element) => element === name);
+}
+
+/**
+ * Extracts the tag name for the JSXAttribute
+ * @param {JSXAttribute} node - JSXAttribute being tested.
+ * @returns {string | null} tag name
+ */
+function getTagName(node) {
+ if (
+ node
+ && node.parent
+ && node.parent.name
+ ) {
+ return node.parent.name.name;
+ }
+ return null;
+}
+
+/**
+ * Test wether the tag name for the JSXAttribute is
+ * something like
+ * @param {JSXAttribute} node - JSXAttribute being tested.
+ * @returns {boolean} result
+ */
+function tagNameHasDot(node) {
+ return !!(
+ node.parent
+ && node.parent.name
+ && node.parent.name.type === 'JSXMemberExpression'
+ );
+}
+
+/**
+ * Get the standard name of the attribute.
+ * @param {string} name - Name of the attribute.
+ * @param {object} context - eslint context
+ * @returns {string | undefined} The standard name of the attribute, or undefined if no standard name was found.
+ */
+function getStandardName(name, context) {
+ if (has(DOM_ATTRIBUTE_NAMES, name)) {
+ return DOM_ATTRIBUTE_NAMES[/** @type {keyof DOM_ATTRIBUTE_NAMES} */ (name)];
+ }
+ if (has(SVGDOM_ATTRIBUTE_NAMES, name)) {
+ return SVGDOM_ATTRIBUTE_NAMES[/** @type {keyof SVGDOM_ATTRIBUTE_NAMES} */ (name)];
+ }
+ const names = getDOMPropertyNames(context);
+
+ // Let's find a possible attribute match with a case-insensitive search.
+ return names.find((element) => element.toLowerCase() === name.toLowerCase());
+}
+
+// ------------------------------------------------------------------------------
+// Rule Definition
+// ------------------------------------------------------------------------------
+
+const messages = {
+ invalidPropOnTag: 'Invalid property \'{{name}}\' found on tag \'{{tagName}}\', but it is only allowed on: {{allowedTags}}',
+ unknownPropWithStandardName: 'Unknown property \'{{name}}\' found, use \'{{standardName}}\' instead',
+ unknownProp: 'Unknown property \'{{name}}\' found',
+ dataLowercaseRequired: 'React does not recognize data-* props with uppercase characters on a DOM element. Found \'{{name}}\', use \'{{lowerCaseName}}\' instead',
+};
+
+/** @type {import('eslint').Rule.RuleModule} */
+module.exports = {
+ meta: {
+ docs: {
+ description: 'Disallow usage of unknown DOM property',
+ category: 'Possible Errors',
+ recommended: true,
+ url: docsUrl('no-unknown-property'),
+ },
+ fixable: 'code',
+
+ messages,
+
+ schema: [{
+ type: 'object',
+ properties: {
+ ignore: {
+ type: 'array',
+ items: {
+ type: 'string',
+ },
+ },
+ requireDataLowercase: {
+ type: 'boolean',
+ default: false,
+ },
+ },
+ additionalProperties: false,
+ }],
+ },
+
+ create(context) {
+ function getIgnoreConfig() {
+ return (context.options[0] && context.options[0].ignore) || DEFAULTS.ignore;
+ }
+
+ function getRequireDataLowercase() {
+ return (context.options[0] && typeof context.options[0].requireDataLowercase !== 'undefined')
+ ? !!context.options[0].requireDataLowercase
+ : DEFAULTS.requireDataLowercase;
+ }
+
+ return {
+ JSXAttribute(node) {
+ const ignoreNames = getIgnoreConfig();
+ const actualName = getText(context, node.name);
+ if (ignoreNames.indexOf(actualName) >= 0) {
+ return;
+ }
+ const name = normalizeAttributeCase(actualName);
+
+ // Ignore tags like
+ if (tagNameHasDot(node)) {
+ return;
+ }
+
+ if (isValidDataAttribute(name)) {
+ if (getRequireDataLowercase() && hasUpperCaseCharacter(name)) {
+ report(context, messages.dataLowercaseRequired, 'dataLowercaseRequired', {
+ node,
+ data: {
+ name: actualName,
+ lowerCaseName: actualName.toLowerCase(),
+ },
+ });
+ }
+
+ return;
+ }
+
+ if (isValidAriaAttribute(name)) { return; }
+
+ const tagName = getTagName(node);
+
+ if (tagName === 'fbt' || tagName === 'fbs') { return; } // fbt/fbs nodes are bonkers, let's not go there
+
+ if (!isValidHTMLTagInJSX(node)) { return; }
+
+ // Let's dive deeper into tags that are HTML/DOM elements (`