Por que podemos excluir algumas propriedades internas do objeto global?


12

Estou lendo es5 hoje em dia e descobri que o atributo [[configurable]] em algumas propriedades internas do objeto global está definido como true, o que significa que podemos excluir essas propriedades.

Por exemplo:

o método de junção do objeto Array.prototype possui atributos

{[[Writable]]:true, [[Enumerable]]: false, [[Configurable]]: true}

Assim, podemos excluir facilmente o método de junção da matriz, como:

delete Array.prototype.join;
alert([1,2,3].join);

O alerta será exibido undefinedno meu cromo 17, firefox 9, ou seja, 10, ou seja, 6;

No Chrome 15 e safari 5.1.1, o atributo [[configurable]] está definido como true e o resultado da exclusão também é verdadeiro, mas o resultado final ainda é function(){[native code]}. Parece que isso é um bug e o cromo corrige.

Eu não percebi isso antes. Na minha opinião, excluir funções internas no código do usuário é perigoso e causará muitos erros ao trabalhar com outras pessoas. Então, por que o ECMAScript toma essa decisão?


Várias respostas elogiam a capacidade de personalizar a funcionalidade interna excluindo propriedades, mas essa abordagem é necessária apenas porque a funcionalidade é conectada às variáveis ​​globais em vez de usar DI. Parece que personalizar ao excluir propriedades é um truque em torno de um design fundamentalmente ruim. Por exemplo, se você precisar alterar o analisador JSON, poderá escrever um código que use um analisador JSON como entrada.
Reintegrar Monica

Respostas:


2

Eu tenderia a concordar com você, mas, por outro lado, acabei de encontrar uma situação em que precisava, delete JSON.stringifyem determinadas circunstâncias, devido a um bug no Firefox 3.5 . Eu certamente estava feliz com a capacidade de consertar macacos embutidos lá.


Por que você simplesmente não o substitui?
Demix #

2
Porque a próxima coisa que acontece é o JSON2.js ser carregado, o que detecta a presença JSON.stringifye a injeta, se necessário. Desculpas, não expliquei isso na minha resposta.
N3dst4

Então, você pode modificar o código fonte de json2.js também, lol
Demix

É uma má idéia modificar bibliotecas de terceiros, porque você não poderá atualizá-las sem copiar todas as suas alterações.
N3dst4

1

Configurável não é sobre exclusão.

É sobre a capacidade de substituir um valor somente leitura.

É uma ferramenta muito poderosa, e os valores não configuráveis ​​são frustrantes se você não puder excluí-los.

Eu tive alguns casos em que precisei corrigir um bug obscuro ou injetar funcionalidades ligeiramente diferentes (interceptação, log). Para isso, é necessário substituir o valor.

Exemplo:

Object.defineProperty(Object.prototype, "foo", {
  value: 42,
  configurable: true
});

var o = {};
o.foo = 50; // fails. foo is not writable
delete Object.prototype.foo;
o.foo = 50; // succeeds
/* optionally put Object.prototype.foo back */

A idéia é que, se você pode excluir propriedades, tem mais controle de metaprogramação. Se você não pudesse excluí-los, ficaria irritado com o idioma.

Não há uma boa razão para tornar as propriedades não deletáveis, a não ser para irritar as pessoas.


1
O atributo [[gravável]] controla a capacidade de alterar o valor.No ES5: [[Gravável]] Boolean Se falso, as tentativas do código ECMAScript de alterar o atributo [[Valor]] da propriedade usando [[Put]] não serão bem-sucedidas. . [[Configurável]] Booleano Se falso, tentar excluir a propriedade, alterar a propriedade para ser uma propriedade do acessador ou alterar seus atributos (exceto [[Valor]]) falhará.
Demix

@demix Sim, isso é correto ...
Raynos

0

..excluir funções internas no código do usuário é perigoso

Pelo contrário. Permitir a personalização é bom porque permite que os autores do site tenham mais flexibilidade.

Se o autor do site precisar carregar o código de terceiros na mesma JS JS e desejar usar o analisador JS incorporado para fazer isso, ele sempre poderá proteger as propriedades configurando-as como não configuráveis ​​antes de carregar o código de terceiros.

Ao utilizar nosso site, você reconhece que leu e compreendeu nossa Política de Cookies e nossa Política de Privacidade.
Licensed under cc by-sa 3.0 with attribution required.