O Chrome vai desativar a modificação de document.domain para relaxar a política de mesma origem

Caso seu site dependa da configuração de document.domain, você precisa realizar uma ação.

Eiji Kitamura
Eiji Kitamura

Atualizações

  • 30 de maio de 2023: anunciamos que a descontinuação do setter do document.domain vai entrar em vigor no Chrome 115.
  • 7 de abril de 2023: identificamos um problema antes de lançar essa mudança no Chrome 112. O setter document.domain a ser removido por padrão está suspenso e o novo marco de envio ainda não foi determinado. Confira esta postagem novamente ou inscreva-se em blink-dev e esta conversa (links em inglês).
  • 20 de janeiro de 2023: cronograma atualizado: o setter document.domain será removido por padrão a partir do Chrome 112. Além disso, foi adicionada uma menção sobre a política corporativa para controlar o comportamento de document.domain.
  • 25 de julho de 2022: cronograma atualizado: o setter document.domain será removido por padrão a partir do Chrome 109.
  • 4 de fevereiro de 2022: atualização com o novo cronograma. Vamos mostrar um aviso no painel "Problemas" a partir do Chrome 100, removendo o setter document.domain por padrão a partir do Chrome 106.
.

document.domain foi projetado para receber ou definir o nome do host da origem.

No Chrome, os sites não podem definir document.domain. Você precisará usar abordagens alternativas, como postMessage() ou a API Channel Messaging, para comunicar origens cruzadas. Queremos que o Chrome 112 envie essa mudança o quanto antes, mas isso depende da resposta à Intent de envio.

Caso seu site dependa do relaxamento de política de mesma origem por document.domain para funcionar corretamente, ele vai precisar enviar um cabeçalho Origin-Agent-Cluster: ?0, assim como todos os outros documentos que exigem esse comportamento. Observe que document.domain não terá efeito se apenas um documento o definir.

Por que tornar document.domain imutável?

Muitos sites configuram o document.domain para permitir a comunicação entre páginas do mesmo site, mas de origem cruzada.

Veja como ele é usado:

Digamos que uma página em https://parent.example.com incorpore uma página de iframe de https://video.example.com. Essas páginas têm o mesmo eTLD+1 (example.com) com subdomínios diferentes. Quando o document.domain das duas páginas é definido como 'example.com', o navegador trata as duas como se fossem da mesma origem.

Defina document.domain como https://parent.example.com:

// Confirm the current origin of "parent.example.com"
console.log(document.domain);

// Set the document.domain
document.domain = 'example.com';
console.log(document.domain);

Defina document.domain como https://video.example.com:

// Confirm the current origin of "video.example.com"
console.log(document.domain);

// Set the document.domain
document.domain = 'example.com';
console.log(document.domain);

Agora é possível criar uma manipulação de DOM de origem cruzada em https://parent.example.com em relação a https://video.example.com.

Os sites definem document.domain para permitir que documentos do mesmo site se comuniquem mais facilmente. Como essa alteração relaxa a política de mesma origem, a página pai pode acessar o documento do iframe e percorrer a árvore DOM e vice-versa.

Essa é uma técnica conveniente, mas apresenta um risco de segurança.

Preocupações de segurança com o app document.domain

As preocupações com a segurança em torno de document.domain levaram a uma mudança na especificação que alerta os usuários para evitar o uso dela (link em inglês). A discussão atual com outros fornecedores de navegadores está avançando na mesma direção.

Por exemplo, quando duas páginas definem document.domain, elas podem fingir que sejam da mesma origem. Isso é especialmente importante quando essas páginas usam um serviço de hospedagem compartilhado com subdomínios diferentes. Definir document.domain abre o acesso a todos os outros sites hospedados pelo mesmo serviço, facilitando o acesso de invasores. Isso é possível porque document.domain ignora a parte do número da porta do domínio.

Para saber mais sobre as implicações de segurança da configuração de document.domain, leia a página"Document.domain" no MDN.

O Chrome planeja tornar document.domain imutável no Chrome 112.

Como saber se meu site será afetado?

Se seu site for afetado por essa mudança, o Chrome vai mostrar um aviso no painel "Issues" do DevTools. Observe a bandeira amarela no canto superior direito.

Quando document.domain é modificado, um aviso é mostrado no painel
"Issues".
Quando document.domain é modificado, um aviso é mostrado no painel "Issues".

Se você tiver um endpoint de relatórios configurado, também receberá relatórios de suspensão de uso. Saiba mais sobre como usar a API Reporting com serviços de coleta de relatórios atuais ou criando sua própria solução interna.

Consulte o site com a auditoria de APIs descontinuadas do LightHouse para encontrar todas as APIs programadas para ser removidas do Chrome.

Comunicação alternativa de origem cruzada

No momento, você tem três opções para substituir o document.domain no seu site.

Usar postMessage() ou a API Channel Messaging

Na maioria dos casos de uso, a postMessage() de origem cruzada ou a API Channel Messaging pode substituir document.domain.

Estes são os elementos do exemplo a seguir:

  1. https://parent.example.com solicita https://video.example.com em um iframe para manipular o DOM enviando uma mensagem via postMessage().
  2. https://video.example.com manipula o DOM assim que recebe a mensagem e notifica o sucesso de volta ao pai.
  3. https://parent.example.com confirma o sucesso.

Em https://parent.example.com:

// Send a message to https://video.example.com
iframe.postMessage('Request DOM manipulation', 'https://video.example.com');

// Receive messages
iframe.addEventListener('message', (event) => {
  // Reject all messages except ones from https://video.example.com
  if (event.origin !== 'https://video.example.com') return;

  // Filter success messages
  if (event.data === 'succeeded') {
    // DOM manipulation is succeeded
  }
});

Em https://video.example.com:

// Receive messages
window.addEventListener('message', (event) => {
  // Reject all messages except ones from https://parent.example.com
  if (event.origin !== 'https://parent.example.com') return;

  // Do a DOM manipulation on https://video.example.com.

  // Send a success message to https://parent.example.com
  event.source.postMessage('succeeded', event.origin);
});

Faça um teste e veja como funciona. Se você tiver requisitos específicos que não funcionem com o postMessage() ou a API Channel Messaging, deixe seu comentário no Twitter via @ChromiumDev ou faça uma pergunta no Stack Overflow com uma tag document.domain.

Como último recurso, envie o cabeçalho Origin-Agent-Cluster: ?0

Se você tiver fortes motivos para continuar configurando document.domain, envie o cabeçalho de resposta Origin-Agent-Cluster: ?0 com o documento de destino.

Origin-Agent-Cluster: ?0

O cabeçalho Origin-Agent-Cluster instrui o navegador se o documento precisa ser manipulado pelo cluster de agente com origin-key. Para saber mais sobre Origin-Agent-Cluster, leia Como solicitar isolamento de desempenho com o cabeçalho Origin-Agent-Cluster.

Ao enviar esse cabeçalho, seu documento pode continuar definindo document.domain mesmo depois que ele se tornar imutável por padrão.

Configurar o OriginAgentClusterDefaultEnabled para a política corporativa

Se preferir, o administrador pode configurar a política OriginAgentClusterDefaultEnabled como false para tornar a configuração document.domain padrão nas instâncias do Chrome em toda a organização. Saiba mais na Lista e gerenciamento de políticas do Chrome Enterprise | Documentação.

Compatibilidade com navegadores

Recursos

Agradecimentos

Foto de Braydon Anderson no Unsplash (links em inglês)