繁体   English   中英

在 DOM 对象上设置属性时如何避免无参数重新分配

[英]How to avoid no-param-reassign when setting a property on a DOM object

我有一个主要目的是在 DOM 对象上设置属性的方法

function (el) {
  el.expando = {};
}

我使用 AirBnB 的代码风格,这使得 ESLint 抛出no-param-reassign错误:

错误分配给函数参数 'el' no-param-reassign

如何在符合 AirBnB 的代码风格的同时操作作为参数传递的 DOM 对象?

有人建议使用/* eslint react/prop-types: 0 */指的是另一个问题,但如果我没记错的话,这适用于 react,但不适用于原生 DOM 操作。

我也不认为改变代码风格是一个答案。 我相信使用标准风格的好处之一是在项目中拥有一致的代码,随意更改规则感觉就像滥用了像 AirBnB 这样的主要代码风格。

作为记录,我在 GitHub 上询问了 AirBnB,他们认为在 issue #766中这些情况下的方法是什么。

正如@Mathletics 所建议的,您可以通过将其添加到您的.eslintrc.json文件中来完全禁用该规则

"rules": {
  "no-param-reassign": 0
}

或者您可以禁用专门针对 param 属性的规则

"rules": {
  "no-param-reassign": [2, { "props": false }]
}

或者,您可以禁用该功能的规则

/* eslint-disable no-param-reassign */
function (el) {
  el.expando = {};
}
/* eslint-enable no-param-reassign */

或仅针对该行

function (el) {
  el.expando = {}; // eslint-disable-line no-param-reassign
}

正如本文所解释的,此规则旨在避免改变arguments对象 如果您分配给一个参数,然后尝试通过arguments对象访问某些参数,则可能会导致意外结果。

您可以通过使用另一个变量来获取对 DOM 元素的引用,然后对其进行修改,从而保持规则不变并保持 AirBnB 样式:

function (el) {
  var theElement = el;
  theElement.expando = {};
}

在 JS 中对象(包括 DOM 节点)是通过引用传递的,所以这里eltheElement是对同一个 DOM 节点的引用,但是修改theElement不会改变arguments对象,因为arguments[0]仍然只是对该 DOM 元素的引用。

规则文档中暗示了这种方法:

此规则的正确代码示例:

/*eslint no-param-reassign: "error"*/

function foo(bar) {
    var baz = bar;
}

就个人而言,我只会使用"no-param-reassign": ["error", { "props": false }]方法来解决提到的其他几个答案。 修改参数的属性不会改变该参数所指的内容,也不应该遇到此规则试图避免的问题。

您可以在.eslintrc文件中覆盖此规则,并为这样的 param 属性禁用它

{
    "rules": {
        "no-param-reassign": [2, { 
            "props": false
        }]
    },
    "extends": "eslint-config-airbnb"
}

这种方式规则仍然有效,但不会对属性发出警告。 更多信息: http : //eslint.org/docs/rules/no-param-reassign

no-param-reassign警告对于常见函数是有意义的,但对于经典的Array.forEach循环,你打算改变它是不合适的。

但是,为了解决这个问题,您还可以将Array.map与一个新对象一起使用(如果您像我一样,不喜欢带有注释的暂停警告):

someArray = someArray.map((_item) => {
    let item = Object.assign({}, _item); // decouple instance
    item.foo = "bar"; // assign a property
    return item; // replace original with new instance
});
function (el) {
  el.setAttribute('expando', {});
}

其他一切都只是丑陋的黑客。

那些希望有选择地停用此规则的人可能会对no-param-reassign规则的拟议新选项感兴趣,该选项将允许对象名称的“白名单”与应忽略哪些参数重新分配有关。

按照文档

function (el) {
  const element = el
  element.expando = {}
}

如果您真的不想禁用规则,则更新的替代方案可能是这样的:

function (el) {
  Object.defineProperty(el, 'expando',{
    value: {},
    writable: true,
    configurable: true,
    enumerable: true
  });
}

参考: https : //developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/defineProperty

您还可以使用 lodash assignIn来改变对象。 assignIn(obj, { someNewObj });

https://lodash.com/docs/4.17.2#assignIn

您可以使用方法来更新数据。 例如。 “res.status(404)”而不是“res.statusCode = 404”我找到了解决方案。 https://github.com/eslint/eslint/issues/6505#issuecomment-282325903

/*eslint no-param-reassign: ["error", { "props": true, "ignorePropertyModificationsFor": ["$scope"] }]*/

app.controller('MyCtrl', function($scope) {
  $scope.something = true;
});

根据 eslint ( https://eslint.org/docs/2.0.0/rules/no-param-reassign ) 上的文档,我使用.eslintrc.js文件中的以下书面配置解决了它。

rules: {
  "no-param-reassign": [2, {"props": false}]
},

您可以使用:

(param) => {
  const data = Object.assign({}, param);
  data.element = 'some value';
}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM