Comment accéder à la méthode Object.prototype dans la logique suivante?

91

J'utilise la logique suivante pour obtenir la chaîne i18n de la clé donnée.

export function i18n(key) {
  if (entries.hasOwnProperty(key)) {
    return entries[key];
  } else if (typeof (Canadarm) !== 'undefined') {
    try {
      throw Error();
    } catch (e) {
      Canadarm.error(entries['dataBuildI18nString'] + key, e);
    }
  }
  return entries[key];
}

J'utilise ESLint dans mon projet. Je reçois l'erreur suivante:

N'accédez pas à la méthode Object.prototype 'hasOwnProperty' à partir de l'objet cible. C'est une erreur « sans prototype intégré ».

Comment modifier mon code pour résoudre cette erreur? Je ne veux pas désactiver cette règle.

booYah
la source
9
Vous devriez probablement lire la documentation. Il existe des exemples de code correct ~ eslint.org/docs/rules/no-prototype-builtins
Phil
1
Vous suggère d'utiliser Object.hasOwnProperty(entries,key)?
passion le
Le code fonctionne correctement. C'est une erreur de peluchage. Je veux juste modifier la syntaxe pour que la règle de linting soit satisfaite.
booYah le
1
@passion Cela stringify entries, ignore keyet vérifie si Objecta une propriété avec cette chaîne.
Oriol

Réponses:

149

Vous pouvez y accéder via Object.prototype:

Object.prototype.hasOwnProperty.call(obj, prop);

Cela devrait être plus sûr, car

  • Tous les objets n'héritent pas de Object.prototype
  • Même pour les objets qui héritent de Object.prototype, la hasOwnPropertyméthode pourrait être ombrée par autre chose.

Bien sûr, le code ci-dessus suppose que

  • Le global Objectn'a pas été ombragé ou redéfini
  • Le natif Object.prototype.hasOwnPropertyn'a pas été redéfini
  • Aucune callpropriété n'a été ajoutée àObject.prototype.hasOwnProperty
  • Le natif Function.prototype.calln'a pas été redéfini

Si l'un de ces éléments ne tient pas, en essayant de coder de manière plus sûre, vous pourriez avoir cassé votre code!

Une autre approche qui n'a pas besoin callserait

!!Object.getOwnPropertyDescriptor(obj, prop);
Oriol
la source
14

Pour votre cas spécifique, les exemples suivants fonctionnent:

if(Object.prototype.hasOwnProperty.call(entries, "key")) {
    //rest of the code
}

OU

if(Object.prototype.isPrototypeOf.call(entries, key)) {
    //rest of the code
}

OU

if({}.propertyIsEnumerable.call(entries, "key")) {
    //rest of the code
}
Zameer Ansari
la source
11

Il semble que cela fonctionnerait également:

key in entries

puisque cela retournera un booléen si la clé existe ou non à l'intérieur de l'objet?

Mike Mathew
la source
3
hasOwnPropertyvérifie si une chaîne ou un symbole est une propriété propre. key in entriesvérifie si elle est propre ou héritée.
Oriol
0

J'espère que je ne serai pas critiqué pour cela, je le ferai probablement, mais!

var a = {b: "I'm here"}
if (a["b"]) { console.log(a["b"]) }
if (a["c"]) { console.log("Never going to happen") }

N'a, pour autant, jamais cassé mon code 😬 Mais je ne suis pas sûr que ce soit le cas dans tous les navigateurs web ...

(De plus, si Canadarmn'est pas défini, votre code semble return entries[key];même si la clé n'est pas dans les entrées ...)

Albert James Teddy
la source
1
Le problème étant que si vous aavez un prototype c, cela arrivera. Js remontera la chaîne de prototypes
Bernardo Dal Corno