tslint / codelyzer / ng lint error: "for (... in ...) заяви повинні бути відфільтровані за допомогою оператора if"


229

Повідомлення про помилку обличчя:

src / app / деталь / edit / edit.component.ts [111, 5]: для (... in ...) операторів потрібно відфільтрувати з оператором if

Фрагмент коду (Це робочий код. Він також доступний у розділі перевірки форми angical.io ):

for (const field in this.formErrors) {
      // clear previous error message (if any)
      this.formErrors[field] = '';
      const control = form.get(field);

      if (control && control.dirty && !control.valid) {
        const messages = this.validationMessages[field];
        for (const key in control.errors) {
          this.formErrors[field] += messages[key] + ' ';
        }
      }
    }

Будь-яка ідея, як виправити цю помилку ворсу?


Може, прийняти відповідь?
Qwertiy

Відповіді:


241

Щоб пояснити актуальну проблему , на яку вказує tslint, цитата з документації JavaScript документа для ... у викладі :

Цикл буде повторювати всі перелічені властивості самого об'єкта та ті, які об'єкт успадковує від прототипу його конструктора (властивості, наближені до об'єкта в ланцюзі прототипу, переосмислюють властивості прототипів).

Отже, в основному це означає, що ви отримаєте властивості, яких ви можете не очікувати (з прототипу ланцюга об'єкта).

Щоб вирішити це, нам потрібно повторити лише власні властивості об'єктів. Ми можемо це зробити двома різними способами (як це запропонували @Maxxx та @Qwertiy).

Перше рішення

for (const field of Object.keys(this.formErrors)) {
    ...
}

Тут ми використовуємо метод Object.Keys (), який повертає масив власних перелічуваних властивостей даного об'єкта в тому ж порядку, що і в циклі for ... in (різниця полягає в тому, що цикл for-in перераховує властивості в також прототип ланцюга).

Друге рішення

for (var field in this.formErrors) {
    if (this.formErrors.hasOwnProperty(field)) {
        ...
    }
}

У цьому рішенні ми повторюємо всі властивості об'єкта, включаючи його в ланцюзі прототипу, але використовуємо метод Object.prototype.hasOwnProperty () , який повертає булеве значення із зазначенням, чи має об'єкт вказане властивість як власне (не успадковане) властивість для фільтрації успадковані властивості виходять.


2
Я хотів би помітити, що Object.keysце ES5. Єдине, що є у ES6 - це цикл for-of. Ми можемо повторити масив у звичайному циклі від 0 до його довжини, і це буде ES5.
Qwertiy

4
ще раз зауважте: якщо якось this.formErrorsце недійсно, for...inпросто нічого не робіть, тоді як for ... of Object.keys()викинете помилку.
користувач3448806

Я дотримуюся другого рішення, але все ще я бачу повідомлення про ворсинки. Час відключеного обличчя.
raj240

2
Чому б не рекомендувати Object.keys(obj).forEach( key => {...}) ?
Бен Карп

268

Акуратніший спосіб застосування відповіді @ Helzgate, можливо, замінить ваш "для .. в"

for (const field of Object.keys(this.formErrors)) {

6
Це має бути прийнятою відповіддю, оскільки вона не тільки вирішує проблему, але також зменшує кількість кодової панелі порівняно з додатковими умовами, такими як if (this.formErrors.hasOwnProperty(field)).
Деніалос

1
Будьте уважні з відповіддю, це може зламати ваші коди. Тестуйте після того, як ви "виправите" це.
ZZZ

3
Це фактично не видаляє помилку tslint для мене.
HammerN'Songs

7
@ HammerN'Songs перевірити , що ви змінили протягом від а для в
Том

та ж проблема тут. помилка не використовується після використання цього
llamerr

71
for (const field in this.formErrors) {
  if (this.formErrors.hasOwnProperty(field)) {
for (const key in control.errors) {
  if (control.errors.hasOwnProperty(key)) {

13

використовувати Object.keys:

Object.keys(this.formErrors).map(key => {
  this.formErrors[key] = '';
  const control = form.get(key);

  if(control && control.dirty && !control.valid) {
    const messages = this.validationMessages[key];
    Object.keys(control.errors).map(key2 => {
      this.formErrors[key] += messages[key2] + ' ';
    });
  }
});

2

Якщо поведінка для (... в ...) прийнятна / необхідна для ваших цілей, ви можете сказати tslint, щоб це дозволило.

в tslint.json, додайте це до розділу "правила".

"forin": false

Інакше @Maxxx має правильну ідею

for (const field of Object.keys(this.formErrors)) {

0

Я думаю, що це повідомлення не стосується уникнення використання switch. Натомість він хоче, щоб ви це перевірили hasOwnProperty. Фон можна прочитати тут: https://stackoverflow.com/a/16735184/1374488

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.