diff --git a/docs/rules/jsx-no-script-url.md b/docs/rules/jsx-no-script-url.md index 8d4f7c8cd4..6e9ec9269d 100644 --- a/docs/rules/jsx-no-script-url.md +++ b/docs/rules/jsx-no-script-url.md @@ -23,6 +23,8 @@ Examples of **correct** code for this rule: ``` +This rule takes into account `linkComponents` setting. + ## Rule Options ```json @@ -44,6 +46,11 @@ Examples of **correct** code for this rule: ``` Allows you to indicate a specific list of properties used by a custom component to be checked. +This will override anything passed to `linkComponents` setting. + +NOTE: This rule now takes into account `linkComponents` setting and it should be used as primary source of link components. +The rule still allows passing link components as rule option, but it is meant only as backwards-compatibility feature. +New setups should only use `linkComponents` setting. ### name diff --git a/lib/rules/jsx-no-script-url.js b/lib/rules/jsx-no-script-url.js index 425741cf1d..73e342c684 100644 --- a/lib/rules/jsx-no-script-url.js +++ b/lib/rules/jsx-no-script-url.js @@ -6,6 +6,7 @@ 'use strict'; const docsUrl = require('../util/docsUrl'); +const linkComponentsUtil = require('../util/linkComponents'); const report = require('../util/report'); // ------------------------------------------------------------------------------ @@ -22,25 +23,25 @@ function hasJavaScriptProtocol(attr) { } function shouldVerifyElement(node, config) { - const name = node.name && node.name.name; - return name === 'a' || config.find((i) => i.name === name); + const name = node.name && node.name.name + return name ? config.has(name) : false } function shouldVerifyProp(node, config) { const name = node.name && node.name.name; const parentName = node.parent.name && node.parent.name.name; - if (parentName === 'a' && name === 'href') { - return true; - } - - const el = config.find((i) => i.name === parentName); - if (!el) { - return false; - } + return (name && parentName) ? name === config.get(parentName) : false +} - const props = el.props || []; - return node.name && props.indexOf(name) !== -1; +function parseLegacyOption(option) { + const config = linkComponentsUtil.getLinkComponents({}) // get defaults + option.forEach(function(opt) { + opt.props.forEach(function(prop) { // FIXME: only last prop will work at the moment + config.set(opt.name, prop) + }) + }) + return config } const messages = { @@ -77,16 +78,18 @@ module.exports = { }, required: ['name', 'props'], additionalProperties: false, + deprecated: true, // ? }, }], }, create(context) { - const config = context.options[0] || []; + const linkComponents = context.options[0] ? parseLegacyOption(context.options[0]) : linkComponentsUtil.getLinkComponents(context); + return { JSXAttribute(node) { const parent = node.parent; - if (shouldVerifyElement(parent, config) && shouldVerifyProp(node, config) && hasJavaScriptProtocol(node)) { + if (shouldVerifyElement(parent, linkComponents) && shouldVerifyProp(node, linkComponents) && hasJavaScriptProtocol(node)) { report(context, messages.noScriptURL, 'noScriptURL', { node, });