UNPKG

@masknet/eslint-plugin

Version:
75 lines (70 loc) 2 kB
import type { TSESTree } from '@typescript-eslint/types' import { createRule } from '../../rule.js' const DEFAULT_LIMIT = 2 export interface Options { attribute: number element: number } export default createRule({ name: 'jsx/no-logical', meta: { type: 'problem', docs: { description: 'Limit the complexity of JSX logic expression', }, schema: [ { oneOf: [ { type: 'integer', minimum: 0 }, { type: 'object', properties: { attribute: { type: 'integer', minimum: 0 }, element: { type: 'integer', minimum: 0 }, }, additionalProperties: false, }, ], }, ], messages: { invalid: 'Limit the complexity of JSX logic expression', }, }, resolveOptions(options?: number | Partial<Options>) { if (typeof options === 'number') { const limit = options ?? DEFAULT_LIMIT return { attribute: limit, element: limit } } const { attribute = DEFAULT_LIMIT, element = DEFAULT_LIMIT } = options ?? {} return { attribute, element } }, create(context, options: Options) { function report(node: TSESTree.JSXExpressionContainer, limit: number) { // prettier-ignore const disallow = node.expression.type === "ConditionalExpression" || getLogicalCount(node.expression) > limit; if (!disallow) return context.report({ node, messageId: 'invalid' }) } return { JSXExpressionContainer(node) { const { parent } = node if (parent?.type === 'JSXAttribute') { report(node, options.attribute) } else if (parent?.type === 'JSXElement') { report(node, options.element) } }, } }, }) function getLogicalCount(node: TSESTree.Node) { if (node.type !== 'LogicalExpression') return 0 let count = 1 while (node.type === 'LogicalExpression') { count += 1 node = node.left } return count }