Experts in Angular

Melhores PráticasBoas Práticas de Segurança no Angular
Angular's built-in protection

Boas Práticas de Segurança no Angular

A história de Angular, como a de qualquer grande inovação, é marcada por desafios e superações. Um dos desafios mais importantes na construção de qualquer aplicação web é garantir a segurança contra vulnerabilidades e ataques, como o temido Cross-Site Scripting (XSS).
Neste artigo, embarcaremos em uma jornada inspiradora pela segurança em Angular, explorando as proteções integradas que a plataforma oferece contra ameaças comuns, assim como as melhores práticas para blindar suas aplicações.

Relatando Vulnerabilidades

O Angular faz parte do programa de recompensa por vulnerabilidades de software de código aberto do Google.
Para vulnerabilidades encontradas no Angular, envie seu relatório em Google Bug Hunters.
Para mais informações sobre como o Google lida com questões de segurança, veja a filosofia de segurança do Google.

A Busca Constante pela Segurança

A segurança em aplicações web, assim como a busca por conhecimento, é uma jornada contínua. A equipe do Angular, em sintonia com a comunidade de código aberto, trabalha incansavelmente para aprimorar as defesas da plataforma e proteger os usuários contra as ameaças em constante evolução.
A cada nova versão, o Angular incorpora atualizações cruciais que podem corrigir falhas de segurança descobertas em versões anteriores. É como um farol que guia os desenvolvedores em direção a um futuro mais seguro.

Mantenha-se Atualizado com as Últimas Versões do Angular

As bibliotecas do Angular recebem atualizações regulares que podem corrigir defeitos de segurança descobertos em versões anteriores. Sempre verifique o log de alterações do Angular para atualizações relacionadas à segurança.

Para construir uma fortaleza digital intransponível, é essencial seguir algumas práticas recomendadas.
Primeiramente, manter-se atualizado com as últimas versões da biblioteca Angular é fundamental.
As atualizações regulares trazem consigo correções de segurança importantes e aprimoramentos que fortalecem a plataforma contra as ameaças mais recentes. É como atualizar as defesas de um castelo medieval para resistir aos avanços tecnológicos dos invasores.

Evite APIs do Angular Marcadas como “Risco de Segurança”

Algumas APIs do Angular são marcadas na documentação como “Risco de Segurança”. É crucial evitar o uso dessas APIs a menos que você compreenda completamente os riscos e tome medidas adequadas para mitigá-los.

Essas APIs, como portais secretos em um castelo, podem ser exploradas por invasores para comprometer a segurança da sua aplicação.

A Ameaça Invisível: Cross-Site Scripting (XSS)

Em nossa jornada pela segurança em Angular, deparamo-nos com um inimigo sorrateiro e perigoso: o Cross-Site Scripting (XSS). Essa ameaça, como um fantasma digital, permite que invasores injetem códigos maliciosos em páginas web, transformando-as em armas contra os próprios usuários.

Imagine um cenário onde um invasor, através de um XSS, consegue roubar dados de login, realizar ações em nome do usuário e até mesmo sequestrar sessões. Essa é a realidade do XSS, um dos ataques mais comuns e devastadores na web. Para proteger nossas aplicações, precisamos entender como esse fantasma opera e como podemos combatê-lo.

O DOM: O Campo de Batalha

O Document Object Model (DOM), a representação da página web em forma de árvore, é o campo de batalha onde o XSS se manifesta. Invasores, através de engenhosas artimanhas, tentam inserir códigos maliciosos no DOM, como a infame tag <script>, que permite a execução de códigos arbitrários na página. Mas o perigo não se limita apenas a essa tag.

Diversos elementos e propriedades no DOM, como o atributo onerror da tag <img> e o atributo href da tag <a>, podem ser explorados para executar códigos maliciosos. É como se o invasor encontrasse brechas nas muralhas do castelo e as utilizasse para infiltrar suas tropas.


A lição é clara: qualquer dado controlado pelo invasor que entre no DOM representa um risco potencial à segurança.

A Defesa Implacável: Prevenção e Vigilância

A prevenção do XSS é uma batalha constante que exige vigilância e conhecimento. A primeira linha de defesa é impedir que códigos maliciosos penetrem no DOM. Isso significa validar e sanitizar todos os dados que entram na aplicação, garantindo que apenas informações seguras e confiáveis sejam processadas.

Em Angular, a plataforma oferece diversas ferramentas e mecanismos para auxiliar nessa batalha.

A sanitização automática de valores, por exemplo, é como um filtro que remove elementos perigosos antes que eles causem danos.

As diretivas de segurança, como o [innerHTML], permitem inserir HTML dinamicamente de forma segura, evitando a execução de scripts indesejados.

Mas a prevenção não é a única arma em nosso arsenal. A detecção precoce de vulnerabilidades é essencial para evitar ataques.
Ferramentas de análise estática de código e testes de segurança, como o SAST (Static Application Security Testing), podem identificar pontos fracos na aplicação antes que eles sejam explorados.
É como ter um sistema de alarme que avisa sobre a presença de invasores antes que eles consigam causar estragos.

Juntos, podemos construir aplicações Angular mais seguras e resilientes, protegendo nossos usuários e dados contra as ameaças do XSS. A batalha continua, mas com conhecimento, vigilância e as ferramentas certas, a vitória é certa.

O Modelo de Segurança do Angular: Uma Fortaleza Contra o XSS

Em sua essência, Angular é uma plataforma construída com a segurança em mente. 

Seu modelo de segurança, como um escudo protetor, oferece uma defesa robusta contra o XSS. Para entender como essa fortaleza funciona, precisamos explorar seus pilares fundamentais.

A Desconfiança como Pilar da Segurança

Angular, como um guardião vigilante, trata todos os valores como não confiáveis por padrão. Essa postura de desconfiança é a base de sua proteção contra o XSS. Ao inserir um valor no DOM, seja através de interpolação ou data binding, Angular assume que ele pode conter códigos maliciosos e o sanitiza automaticamente.

Por exemplo, ao utilizar interpolação ({{}}) ou property binding ([property]="value"), o Angular escapa automaticamente qualquer conteúdo potencialmente perigoso.

Essa sanitização, como um processo de purificação, remove ou neutraliza elementos perigosos antes que eles causem danos.

Mas e se um valor já tiver sido sanitizado fora do Angular e for considerado seguro? Nesse caso, você pode informar ao Angular sobre a confiabilidade do valor, marcando-o como confiável. É como apresentar um salvo-conduto que garante a passagem segura do valor pelo sistema.

Templates Confiáveis: A Exceção à Regra

Ao contrário dos valores utilizados para renderização, os templates do Angular são considerados confiáveis por padrão. Eles são como plantas de um projeto arquitetônico, contendo instruções precisas sobre como construir a interface da aplicação.

Criar templates concatenando entradas do usuário com a sintaxe do template é uma prática perigosa. É como permitir que um estranho desenhe os planos de sua casa, abrindo caminho para armadilhas e vulnerabilidades.
Para evitar essa ameaça, utilize sempre o compilador de templates Ahead-Of-Time (AOT) em ambientes de produção. Essa ferramenta, como um mestre construtor experiente, verifica e valida os templates antes de executá-los, garantindo a segurança da estrutura.

Compilador de Templates Ahead-Of-Time (AOT)

O compilador AOT pré-compila os templates do Angular durante o processo de build, transformando-os em código JavaScript eficiente. Isso não só melhora a performance da aplicação, mas também ajuda a prevenir injeções de código em tempo de execução.

// Exemplo de configuração do AOT no Angular
"angularCompilerOptions": {
  "enableIvy": true,
  "strictTemplates": true
}

Content Security Policy e Trusted Types: A Guarda Avançada

Para fortalecer ainda mais as defesas contra o XSS, Angular oferece suporte a duas tecnologias avançadas: Content Security Policy (CSP) e Trusted Types.
Essas ferramentas, como uma guarda avançada, operam no nível do DOM, o ponto mais eficaz para prevenir ataques XSS. Elas são capazes de bloquear a execução de scripts maliciosos e garantir a integridade dos dados, mesmo que outras APIs de nível inferior sejam utilizadas.

Configurar o CSP e habilitar o Trusted Types é como adicionar camadas extras de segurança à sua aplicação. O CSP, como um conjunto de regras de segurança, define quais fontes de conteúdo são permitidas e quais são bloqueadas. O Trusted Types, por sua vez, garante que apenas valores confiáveis sejam utilizados em contextos sensíveis, como a inserção de HTML dinâmico.

Implementando a Política de Segurança de Conteúdo (CSP)

A CSP permite que você controle quais recursos podem ser carregados e executados em sua aplicação, limitando a capacidade de um invasor de injetar código malicioso. Aqui está um exemplo de configuração de CSP:

<meta http-equiv="Content-Security-Policy" content="default-src 'self'; script-src 'self' https://trusted.cdn.com; object-src 'none';">

Habilitando Trusted Types

Trusted Types é uma API que ajuda a prevenir XSS ao restringir como o conteúdo dinâmico pode ser inserido no DOM. Habilitar Trusted Types em sua aplicação Angular pode aumentar significativamente a segurança:

<script>
  TrustedTypes.createPolicy('default', {
    createHTML: (input) => {
      // Implementar sanitização aqui
      return DOMPurify.sanitize(input);
    }
  });
</script>

Sanitização e Contextos de Segurança: A Arte de Purificar Dados

Em nossa jornada, chegamos a um ponto crucial: a sanitização de dados. Essa técnica, como um processo de alquimia digital, transforma valores não confiáveis em valores seguros para inserção no DOM. Mas como essa mágica funciona?

A Importância do Contexto

A sanitização não é um processo único e universal. Ela depende do contexto em que o valor será utilizado. Um valor inofensivo em CSS pode ser perigoso em uma URL. É como um ingrediente que pode ser saboroso em um prato, mas venenoso em outro.

Angular define quatro contextos de segurança: HTML, Style, URL e Resource URL. Cada contexto possui suas próprias regras de sanitização, adaptadas às particularidades de cada tipo de dado.

  • HTML: Utilizado ao interpretar um valor como HTML, por exemplo, ao fazer o binding com a propriedade innerHTML. Nesse contexto, a sanitização remove tags e atributos perigosos, como <script> e onerror.
  • Style: Utilizado ao inserir CSS na propriedade style. A sanitização nesse contexto remove propriedades perigosas, como expression e behavior.
  • URL: Utilizado para propriedades de URL, como <a href>. A sanitização verifica se a URL possui um protocolo seguro (https) e remove caracteres especiais que poderiam ser utilizados para executar scripts.
  • Resource URL: Utilizado para URLs que são carregadas e executadas como código, como em <script src>. A sanitização nesse contexto não é possível, pois a URL pode conter código arbitrário.

A Mão Protetora do Angular

Angular se encarrega de sanitizar automaticamente valores não confiáveis para os contextos HTML e URL. É como um filtro que remove impurezas antes que elas contaminem o sistema. Em modo de desenvolvimento, Angular exibe um aviso no console quando precisa modificar um valor durante a sanitização, alertando o desenvolvedor sobre possíveis riscos.

Essa proteção automática é essencial para prevenir ataques XSS. Ao sanitizar os dados antes de inseri-los no DOM, Angular garante que apenas informações seguras e confiáveis sejam exibidas aos usuários. É como ter um guardião que protege a entrada do castelo, impedindo a entrada de intrusos.

No entanto, a sanitização não é infalível. É importante ter em mente que a segurança é uma responsabilidade compartilhada entre a plataforma e o desenvolvedor. Ao utilizar dados externos em sua aplicação, certifique-se de que eles sejam provenientes de fontes confiáveis e que tenham sido devidamente validados e sanitizados.

Com a sanitização e os contextos de segurança, Angular oferece uma camada adicional de proteção contra o XSS. Ao compreender como essa ferramenta funciona e como utilizá-la corretamente, você estará dando um passo importante para construir aplicações mais seguras e resilientes.

Sanitização em Ação: Um Exemplo Prático

Para tornar a sanitização mais tangível, vamos explorar um exemplo prático de como o Angular protege sua aplicação contra o XSS. Imagine o seguinte template, que realiza o binding do valor da variável htmlSnippet de duas formas: interpolando-o no conteúdo de um elemento e através da propriedade innerHTML:

<h3>Binding innerHTML</h3>
<p>Bound value:</p>
<p class="e2e-inner-html-interpolated">{{ htmlSnippet }}</p>
<p>Result of binding to innerHTML:</p>
<p class="e2e-inner-html-bound" [innerHTML]="htmlSnippet"></p>

No componente TypeScript correspondente, a variável htmlSnippet recebe um valor que poderia ser controlado por um invasor, contendo um script malicioso:

export class InnerHtmlBindingComponent {
  // For example, a user/attacker-controlled value from a URL.
  htmlSnippet = 'Template <script>alert("0wned")</script> <b>Syntax</b>';
}

A Mágica da Sanitização

Ao executar este código, você notará que o conteúdo interpolado é automaticamente escapado. Isso significa que o HTML não é interpretado, e o navegador exibe os sinais de maior e menor (< e >) como texto. Essa é a primeira linha de defesa do Angular contra o XSS.

No entanto, para que o HTML seja interpretado, ele precisa ser ligado a uma propriedade HTML, como innerHTML. Mas cuidado! Fazer o binding de um valor controlado por um invasor para innerHTML normalmente causaria uma vulnerabilidade XSS. O script malicioso seria executado, comprometendo a segurança da aplicação.

É aqui que a sanitização do Angular entra em ação. Ao detectar que o valor de htmlSnippet é potencialmente perigoso, Angular o sanitiza automaticamente, removendo o elemento <script> e mantendo apenas o conteúdo seguro, como o elemento <b>. Dessa forma, o ataque XSS é neutralizado, e a aplicação permanece segura.

A Lição Aprendida

Este exemplo demonstra a importância da sanitização e como o Angular a utiliza para proteger sua aplicação. Ao escapar automaticamente o conteúdo interpolado e sanitizar valores ligados a propriedades HTML, Angular impede que códigos maliciosos sejam executados, garantindo a segurança dos seus usuários e dados.

Lembre-se que a sanitização é apenas uma das ferramentas de segurança do Angular. Para construir aplicações verdadeiramente seguras, é preciso combinar a sanitização com outras práticas, como validar dados de entrada, utilizar diretivas de segurança e manter-se atualizado com as últimas versões do Angular.

Com este exemplo, esperamos ter elucidado o conceito de sanitização e como ele se aplica na prática. A jornada pela segurança em Angular continua, e a cada passo, estamos mais preparados para enfrentar os desafios e construir aplicações mais resilientes e confiáveis.

APIs do DOM e Sanitização Explícita: Navegando em Águas Turbulentas

Em nossa jornada, encontramos um caminho mais desafiador: o uso direto das APIs do DOM. Essa prática, como navegar em águas turbulentas, exige cautela e conhecimento, pois as APIs nativas do navegador, como o objeto document e o nó ElementRef, não oferecem proteção automática contra vulnerabilidades de segurança.

O Perigo da Interação Direta

Ao interagir diretamente com o DOM, você se expõe a métodos inseguros que podem ser explorados por invasores. Além disso, bibliotecas de terceiros que manipulam o DOM podem não oferecer a mesma sanitização automática que as interpolações do Angular. É como aventurar-se em terras desconhecidas sem um guia experiente.

Por isso, evite a interação direta com o DOM sempre que possível. Utilize templates do Angular, que oferecem uma camada de segurança adicional através da sanitização automática. É como seguir um mapa confiável que o conduz por caminhos seguros.

A Ferramenta Essencial: DomSanitizer

Em situações onde a interação direta com o DOM é inevitável, o Angular oferece uma ferramenta poderosa: a classe DomSanitizer. Essa classe, como um kit de primeiros socorros, permite sanitizar valores não confiáveis antes de inseri-los no DOM.

Para utilizar o DomSanitizer, basta injetá-lo em seu componente e chamar o método sanitize, passando o valor a ser sanitizado e o contexto de segurança adequado. Essa função também aceita valores marcados como confiáveis, como descrito na seção anterior, e não os sanitiza.

import { Component, OnInit } from '@angular/core';
import { DomSanitizer, SafeHtml } from '@angular/platform-browser';

@Component({ /* ... */ })
export class AppComponent implements OnInit {
  dangerousHtml: string = 'Template <script>alert("0wned")</script> <b>Syntax</b>';
  safeHtml: SafeHtml;

  constructor(private sanitizer: DomSanitizer) {}

  ngOnInit() {
    this.safeHtml = this.sanitizer.sanitize(SecurityContext.HTML, this.dangerousHtml);
  }
}

A Importância da Cautela

Ao utilizar o DomSanitizer, é fundamental ter cautela. Certifique-se de que os valores a serem sanitizados são realmente não confiáveis e que o contexto de segurança escolhido é adequado. Utilizar o contexto errado pode levar a uma sanitização inadequada, abrindo brechas para ataques XSS. É como aplicar um medicamento sem o diagnóstico correto.

Lembre-se que a segurança é uma responsabilidade contínua. Ao trabalhar com APIs do DOM, esteja sempre atento aos riscos e utilize as ferramentas de sanitização do Angular para proteger sua aplicação e seus usuários. Com conhecimento e cuidado, você pode navegar pelas águas turbulentas do DOM com segurança e confiança.

Confiando em Valores Seguros: Uma Abordagem Cautelosa

Em certas ocasiões, sua aplicação pode precisar incluir código executável, exibir um <iframe> de uma URL externa ou construir URLs potencialmente perigosas. Nesses casos, a sanitização automática do Angular pode ser um obstáculo. Para contornar essa situação, você pode informar ao Angular que inspecionou e validou um valor, garantindo sua segurança.

Uma Responsabilidade Crucial

É fundamental ter cuidado ao confiar em valores externos. Se você confiar em um valor malicioso, estará introduzindo uma vulnerabilidade em sua aplicação. Em caso de dúvida, consulte um especialista em segurança.

Para marcar um valor como confiável, utilize o DomSanitizer e chame um dos seguintes métodos:

  • bypassSecurityTrustHtml
  • bypassSecurityTrustScript
  • bypassSecurityTrustStyle
  • bypassSecurityTrustUrl
  • bypassSecurityTrustResourceUrl

Lembre-se de que a segurança de um valor depende do contexto. Escolha o contexto correto para o uso pretendido.

Exemplo: Confiando em uma URL

Imagine que seu template precisa vincular uma URL a uma chamada javascript:alert(...). Normalmente, o Angular sanitizaria a URL, desabilitando o código perigoso. Para evitar isso, marque o valor da URL como confiável usando bypassSecurityTrustUrl:

constructor(private sanitizer: DomSanitizer) {
  // javascript: URLs are dangerous if attacker controlled.
  this.dangerousUrl = 'javascript:alert("Hi there")';
  this.trustedUrl = sanitizer.bypassSecurityTrustUrl(this.dangerousUrl);
}

Convertendo Entrada do Usuário em Valor Confiável

Se você precisar converter a entrada do usuário em um valor confiável, use um método de componente. O template a seguir permite que os usuários insiram um ID de vídeo do YouTube e carreguem o vídeo correspondente em um <iframe>. O atributo src do <iframe> é um contexto de segurança de URL de recurso, pois uma fonte não confiável pode, por exemplo, contrabandear downloads de arquivos que usuários desavisados poderiam executar.
Para evitar isso, chame um método no componente para construir uma URL de vídeo confiável, o que faz com que o Angular permita a vinculação ao src do <iframe>:

Template: bypass-security.component.html (iframe)

<h4>Resource URL:</h4>
<p>Showing: {{ dangerousVideoUrl }}</p>

<p>Trusted:</p>
<iframe class="e2e-iframe-trusted-src" width="640" height="390" [src]="videoUrl" title="trusted video url"></iframe>

<p>Untrusted:</p>
<iframe class="e2e-iframe-untrusted-src" width="640" height="390" [src]="dangerousVideoUrl" title="unTrusted video url"></iframe>

Classe: bypass-security.component.ts (trust-video-url)

import { Component } from '@angular/core';
import { DomSanitizer } from '@angular/platform-browser';

@Component({
  selector: 'app-bypass-security',
  templateUrl: './bypass-security.component.html'
})
export class BypassSecurityComponent {
  dangerousVideoUrl: string;
  videoUrl: any;

  constructor(private sanitizer: DomSanitizer) {}

  updateVideoUrl(id: string) {
    // Adicionar um ID a uma URL do YouTube é seguro.
    // Sempre certifique-se de construir objetos SafeValue
    // o mais próximo possível dos dados de entrada para
    // que seja mais fácil verificar se o valor é seguro.
    this.dangerousVideoUrl = 'https://www.youtube.com/embed/' + id;
    this.videoUrl = this.sanitizer.bypassSecurityTrustResourceUrl(this.dangerousVideoUrl);
  }
}

A Importância da Validação

Ao converter a entrada do usuário em um valor confiável, utilize um método do componente. Isso permite validar a entrada antes de marcá-la como confiável, adicionando uma camada extra de segurança. Construa objetos SafeValue o mais próximo possível dos dados de entrada, facilitando a verificação da segurança do valor.

Lembre-se, a confiança em valores externos deve ser tratada com cautela. Ao seguir as melhores práticas e utilizar as ferramentas de segurança do Angular, você estará construindo aplicações mais seguras e protegendo seus usuários de ameaças em potencial.

Content Security Policy (CSP): Uma Camada Extra de Proteção

Em nossa busca por uma segurança robusta, encontramos uma poderosa ferramenta: a Content Security Policy (CSP). Essa técnica, como um escudo adicional, fortalece a defesa contra ataques XSS, adicionando uma camada extra de proteção à sua aplicação Angular.

O Que é CSP?

A CSP é uma técnica de segurança em profundidade que permite controlar as fontes de conteúdo que podem ser carregadas e executadas em sua aplicação. Através de um cabeçalho HTTP Content-Security-Policy, você define regras que determinam quais scripts, estilos, imagens e outros recursos são permitidos, e de quais origens eles podem vir.

Configurando o CSP para Angular

Para habilitar o CSP em sua aplicação Angular, você precisa configurar seu servidor web para retornar o cabeçalho Content-Security-Policy em cada requisição. A política mínima necessária para uma nova aplicação Angular é:

default-src 'self'; style-src 'self' 'nonce-randomNonceGoesHere'; script-src 'self' 'nonce-randomNonceGoesHere';

Essa política permite que a página carregue todos os seus recursos da mesma origem ('self') e define regras específicas para estilos e scripts. Para evitar ataques XSS, é crucial incluir um nonce (um valor aleatório gerado para cada requisição) nas seções style-src e script-src.

Integrando o Nonce com Angular

Para que o Angular possa renderizar elementos <style> com segurança, você precisa fornecer o nonce gerado pelo servidor. Existem duas maneiras de fazer isso:

  1. Definindo o atributo ngCspNonce: Adicione o atributo ngCspNonce ao elemento raiz da sua aplicação, passando o valor do nonce gerado pelo servidor. Essa abordagem é ideal quando você tem acesso a um sistema de templates no servidor que pode adicionar o nonce tanto ao cabeçalho quanto ao arquivo index.html.
  2. Utilizando o token de injeção CSP_NONCE: Essa abordagem é útil quando você tem acesso ao nonce em tempo de execução e deseja armazenar o index.html em cache. Você pode fornecer o nonce ao Angular através do token de injeção CSP_NONCE:

Definir o atributo ngCspNonce no elemento raiz da aplicação:

<app ngCspNonce="randomNonceGoesHere"></app>

Use essa abordagem se você tiver acesso ao template do lado do servidor que pode adicionar o nonce tanto ao cabeçalho quanto ao index.html ao construir a resposta.

Fornecer o nonce usando o token de injeção CSP_NONCE:

import { bootstrapApplication, CSP_NONCE } from '@angular/core';
import { AppComponent } from './app/app.component';

bootstrapApplication(AppComponent, {
  providers: [{
    provide: CSP_NONCE,
    useValue: globalThis.myRandomNonceValue
  }]
});

Use essa abordagem se você tiver acesso ao nonce em tempo de execução e deseja poder armazenar em cache o index.html.

A Importância da Unicidade do Nonce

É fundamental garantir que os nonces fornecidos sejam únicos para cada requisição e que não sejam previsíveis ou fáceis de adivinhar. Se um invasor puder prever os nonces futuros, ele poderá contornar a proteção oferecida pelo CSP.

Expandindo as Configurações do CSP

À medida que seu projeto cresce, você pode precisar expandir as configurações do CSP para acomodar recursos e funcionalidades específicas da sua aplicação. Consulte a documentação do CSP para obter informações detalhadas sobre as diretivas disponíveis e como utilizá-las.

Ao combinar o modelo de segurança do Angular com a Content Security Policy, você estará construindo uma fortaleza digital ainda mais robusta, protegendo seus usuários e dados de forma eficaz contra ataques XSS e outras ameaças.

Trusted Types: Reforçando a Segurança Contra XSS

Em nossa busca por aprimorar a segurança de aplicações Angular, deparamo-nos com uma ferramenta poderosa: o Trusted Types. Essa tecnologia, como um guardião da integridade do DOM, impõe práticas de codificação mais seguras e simplifica a auditoria do código, tornando-o mais resistente a ataques XSS.

O Que São Trusted Types?

Trusted Types é um recurso da plataforma web que permite definir políticas de segurança para a manipulação do DOM. Ao habilitar o Trusted Types, você garante que apenas valores confiáveis, criados através de APIs específicas, sejam inseridos em contextos sensíveis do DOM, como a propriedade innerHTML. Essa abordagem previne a injeção de scripts maliciosos e garante a integridade dos dados.

Compatibilidade com Navegadores

É importante ressaltar que o Trusted Types ainda não está disponível em todos os navegadores. No entanto, se sua aplicação habilitada para Trusted Types for executada em um navegador que não o suporta, os recursos da aplicação serão preservados, e a proteção contra XSS será garantida pelo DomSanitizer do Angular. Consulte o site caniuse.com/trusted-types para verificar a compatibilidade atual.

Implementando Trusted Types em Angular

Para habilitar o Trusted Types em sua aplicação Angular, você precisa configurar o servidor web para emitir cabeçalhos HTTP com uma das seguintes políticas do Angular:

  • angular: Esta política é utilizada em código revisado por segurança e é necessária para o funcionamento do Angular quando o Trusted Types está ativo.
  • angular#unsafe-bypass: Esta política é utilizada em aplicações que usam métodos do DomSanitizer que ignoram a segurança, como o bypassSecurityTrustHtml.
  • angular#unsafe-jit: Esta política é utilizada pelo compilador Just-In-Time (JIT).
  • angular#bundler: Esta política é utilizada pelo Angular CLI ao criar arquivos de chunk preguiçosos.

Você deve configurar os cabeçalhos HTTP para Trusted Types nos seguintes locais:

  • Infraestrutura de produção
  • Angular CLI (ng serve), usando a propriedade headers no arquivo angular.json, para desenvolvimento local e testes de ponta a ponta
  • Karma (ng test), usando a propriedade customHeaders no arquivo karma.config.js, para testes unitários

Exemplos de Cabeçalhos HTTP

  • Para aplicações Angular que não utilizam métodos inseguros do DomSanitizer:
Content-Security-Policy: trusted-types angular; require-trusted-types-for 'script';
  • Para aplicações Angular que utilizam métodos inseguros do DomSanitizer:
Content-Security-Policy: trusted-types angular angular#unsafe-bypass; require-trusted-types-for 'script';
  • Para aplicações Angular que utilizam o compilador JIT:
Content-Security-Policy: trusted-types angular angular#unsafe-jit; require-trusted-types-for 'script';
  • Para aplicações Angular que utilizam carregamento preguiçoso de módulos:
Content-Security-Policy: trusted-types angular angular#bundler; require-trusted-types-for 'script';

Contribuições da Comunidade

Para saber mais sobre como resolver problemas de configuração de Trusted Types, o recurso a seguir pode ser útil: Prevent DOM-based cross-site scripting vulnerabilities with Trusted Types.

Um Passo Além na Segurança

Ao combinar o Trusted Types com as outras ferramentas de segurança do Angular, como a sanitização e o Content Security Policy, você estará elevando a segurança da sua aplicação a um novo patamar. Essa abordagem proativa e em camadas garante que sua aplicação esteja protegida contra as ameaças mais sofisticadas, proporcionando tranquilidade para você e seus usuários.

O Compilador de Templates AOT: Blindagem Contra Injeção de Templates

Em nossa jornada pela segurança em Angular, encontramos uma ferramenta essencial: o compilador de templates Ahead-Of-Time (AOT). Essa poderosa ferramenta não apenas melhora o desempenho da aplicação, mas também previne uma classe inteira de vulnerabilidades conhecida como injeção de templates.

AOT vs JIT: Uma Escolha Crucial

O compilador AOT é o padrão utilizado em aplicações Angular CLI e deve ser usado em todos os ambientes de produção. Ele compila os templates em código executável durante o processo de build, antes da aplicação ser executada no navegador. Essa abordagem oferece diversas vantagens em termos de segurança e performance.

Uma alternativa ao compilador AOT é o compilador Just-In-Time (JIT), que compila os templates em tempo de execução, dentro do navegador. No entanto, essa prática pode ser perigosa, pois o Angular confia no código do template. Gerar templates dinamicamente e compilá-los, especialmente aqueles que contêm dados do usuário, pode contornar as proteções integradas do Angular, abrindo caminho para ataques de injeção de templates.

Injeção de Templates: Um Perigo Real

A injeção de templates é uma vulnerabilidade que permite a um invasor injetar código malicioso nos templates da sua aplicação. Esse código pode ser executado no contexto da aplicação, permitindo ao invasor roubar dados, realizar ações em nome do usuário e até mesmo controlar a aplicação inteira.

Ao utilizar o compilador AOT, você impede que templates sejam gerados dinamicamente, eliminando essa vulnerabilidade. Além disso, o AOT melhora o desempenho da aplicação, pois os templates já estão compilados e prontos para serem executados.

Construindo Formulários Dinâmicos com Segurança

Em algumas situações, pode ser necessário construir formulários dinamicamente em sua aplicação Angular. Para fazer isso de forma segura, siga as recomendações do guia de Formulários Dinâmicos do Angular. Este guia oferece técnicas e exemplos de como criar formulários flexíveis e seguros, sem comprometer a segurança da sua aplicação.

AOT: Um Pilar da Segurança em Angular

O compilador de templates AOT é um pilar fundamental da segurança em Angular. Ao utilizá-lo em seus projetos, você estará protegendo sua aplicação contra injeção de templates e outras vulnerabilidades, garantindo a segurança dos seus usuários e dados.

Exemplo de Configuração do AOT no Angular CLI

O Angular CLI está configurado para usar o compilador AOT por padrão. Veja como garantir que o AOT esteja habilitado:

  1. Arquivo angular.json: Certifique-se de que a opção "aot": true esteja definida nas configurações de build:
{
  "projects": {
    "your-project-name": {
      "architect": {
        "build": {
          "configurations": {
            "production": {
              "aot": true
            }
          }
        },
        "serve": {
          "configurations": {
            "production": {
              "browserTarget": "your-project-name:build:production"
            }
          }
        }
      }
    }
  }
}

2. Comando de Build: Utilize o comando de build com a configuração de produção:

ng build --prod

Construção Dinâmica de Formulários de Forma Segura

Para informações sobre como construir formulários dinamicamente de forma segura, consulte o guia de Formulários Dinâmicos.

Proteção XSS no Lado do Servidor: Blindando a Origem

Em nossa jornada pela segurança, chegamos a um ponto crucial: a proteção XSS no lado do servidor. Assim como proteger a fonte de um rio garante a pureza de suas águas, proteger o HTML construído no servidor é essencial para prevenir ataques de injeção em sua aplicação Angular.

O Perigo da Injeção de Templates

A injeção de código de template em uma aplicação Angular é tão perigosa quanto injetar código executável. Ambas as ações concedem ao invasor controle total sobre a aplicação, permitindo a execução de ações maliciosas, roubo de dados e manipulação da interface.

Para evitar essa ameaça, é fundamental utilizar uma linguagem de templates que escape automaticamente os valores, prevenindo vulnerabilidades XSS no servidor. Linguagens como Jinja2 (Python), Pug (Node.js) e Twig (PHP) oferecem recursos de escape que protegem sua aplicação contra a injeção de código malicioso.

A Armadilha dos Templates no Lado do Servidor

Criar templates Angular no lado do servidor utilizando uma linguagem de templates é uma prática arriscada. Essa abordagem aumenta o risco de introduzir vulnerabilidades de injeção de templates, pois o código gerado pode não ser devidamente sanitizado.

Em vez disso, utilize o compilador AOT do Angular, que garante a segurança dos templates e melhora o desempenho da aplicação. O AOT compila os templates em código executável antes da aplicação ser executada no navegador, impedindo a injeção de código malicioso.

A Fortaleza da Segurança em Camadas

A proteção XSS no lado do servidor é apenas uma das camadas de segurança que você deve implementar em sua aplicação Angular. Combinar essa proteção com as ferramentas e técnicas apresentadas anteriormente, como a sanitização, o Content Security Policy e o Trusted Types, cria uma fortaleza digital que protege sua aplicação e seus usuários de forma abrangente.

Lembre-se que a segurança é um processo contínuo. Esteja sempre atento às últimas vulnerabilidades e atualize suas ferramentas e práticas de segurança regularmente. Ao construir uma aplicação Angular segura desde a sua base, você garante a confiança dos seus usuários e protege seus dados de forma eficaz.

Vulnerabilidades em Nível HTTP: Desvendando as Armadilhas da Web

Em nossa jornada pela segurança em Angular, adentramos um território repleto de perigos: as vulnerabilidades em nível HTTP. Como navegadores desbravando mares desconhecidos, nossas aplicações podem ser vítimas de ataques como a falsificação de solicitação entre sites (CSRF ou XSRF) e a inclusão de script entre sites (XSSI).

Felizmente, o Angular oferece recursos integrados para auxiliar na prevenção dessas ameaças, trabalhando em conjunto com o servidor para garantir a segurança da sua aplicação.

Falsificação de Solicitação Entre Sites (CSRF ou XSRF): O Inimigo Invisível

Imagine um cenário onde um invasor, como um pirata digital, engana o usuário a visitar uma página web maliciosa (evil.com) que, por sua vez, envia uma solicitação secreta ao servidor da sua aplicação (example-bank.com).

Suponha que o usuário esteja logado em example-bank.com. Ao clicar em um link malicioso em um e-mail, uma nova aba se abre com a página evil.com. Essa página, em segundo plano, envia uma solicitação maliciosa para example-bank.com, como uma transferência de dinheiro da conta do usuário para a conta do invasor. O navegador, inocentemente, envia os cookies de example-bank.com, incluindo o cookie de autenticação, junto com a solicitação.

Se o servidor de example-bank.com não possuir proteção contra XSRF, ele não conseguirá distinguir entre uma solicitação legítima da aplicação e a solicitação forjada de evil.com, tornando-se vítima do ataque.

A Solução: Uma Parceria entre Cliente e Servidor

Para prevenir o CSRF, a aplicação deve garantir que a solicitação do usuário se origine da aplicação real, e não de um site diferente. Essa batalha exige uma parceria entre o servidor e o cliente.

Uma técnica comum de proteção contra XSRF envolve o servidor enviar um token de autenticação aleatório em um cookie. O código do cliente lê o cookie e adiciona um cabeçalho de solicitação personalizado com o token em todas as solicitações subsequentes. O servidor compara o valor do cookie recebido com o valor do cabeçalho da solicitação, rejeitando a solicitação caso os valores não coincidam.

Essa técnica é eficaz graças à política de mesma origem implementada pelos navegadores. Somente o código do site onde os cookies são definidos pode ler esses cookies e definir cabeçalhos personalizados em solicitações para esse site. Isso significa que apenas a sua aplicação pode ler o token do cookie e definir o cabeçalho personalizado, enquanto o código malicioso em evil.com não consegue.

Angular: Seu Aliado na Proteção Contra CSRF

Angular oferece recursos que facilitam a implementação dessa técnica de proteção. O módulo HttpClientXsrfModule adiciona automaticamente um cabeçalho XSRF às solicitações HTTP, enquanto o interceptor HttpXsrfInterceptor lê o token XSRF de um cookie e o adiciona ao cabeçalho.

Ao utilizar esses recursos, você adiciona uma camada extra de segurança à sua aplicação Angular, protegendo seus usuários de ataques CSRF.

HttpClient e a Segurança XSRF/CSRF: Uma Barreira Contra Ataques

Em nossa jornada, exploramos como o Angular oferece suporte a um mecanismo comum para prevenir ataques XSRF/CSRF. Ao realizar requisições HTTP, um interceptor lê um token de um cookie, por padrão chamado XSRF-TOKEN, e o define como um cabeçalho HTTP X-XSRF-TOKEN.

O Poder da Política de Mesma Origem

Essa técnica se baseia na política de mesma origem da web, que impede que um site malicioso acesse cookies de outro site. Assim, apenas o código executado no seu domínio pode ler o cookie XSRF-TOKEN e definir o cabeçalho correspondente, garantindo que a requisição HTTP tenha origem na sua aplicação e não em um invasor.

Por Que Não Proteger Requisições GET?

A proteção CSRF é necessária apenas para requisições que podem alterar o estado no backend. Ataques CSRF, por natureza, cruzam os limites de domínio, e a política de mesma origem impede que uma página maliciosa recupere os resultados de requisições GET autenticadas.

O Papel do Backend

Para que essa proteção funcione, seu servidor precisa definir um token em um cookie de sessão legível por JavaScript chamado XSRF-TOKEN, seja no carregamento da página ou na primeira requisição GET. Em requisições subsequentes, o servidor pode verificar se o cookie corresponde ao cabeçalho HTTP X-XSRF-TOKEN, garantindo que apenas o código em execução no seu domínio poderia ter enviado a requisição.

O token deve ser único para cada usuário e verificável pelo servidor, impedindo que o cliente crie seus próprios tokens. Para maior segurança, defina o token como um hash do cookie de autenticação do seu site com um salt.

Múltiplas Aplicações Angular no Mesmo Domínio

Em ambientes onde várias aplicações Angular compartilham o mesmo domínio ou subdomínio, atribua um nome de cookie exclusivo para cada aplicação, a fim de evitar colisões e garantir a eficácia da proteção XSRF.

A Responsabilidade do Backend

É importante ressaltar que o HttpClient do Angular oferece apenas a metade da proteção XSRF. Seu serviço de backend deve ser configurado para definir o cookie na página e verificar a presença do cabeçalho em todas as requisições elegíveis. Caso contrário, a proteção padrão do Angular será ineficaz.

Uma Parceria Essencial

A proteção XSRF/CSRF é uma parceria entre o cliente e o servidor. O Angular facilita a implementação da parte do cliente, mas a configuração correta do backend é crucial para garantir a segurança da sua aplicação. Ao trabalhar em conjunto, você cria uma barreira robusta contra ataques CSRF, protegendo seus usuários e dados.

Personalizando a Proteção XSRF/CSRF: Adaptando-se às suas Necessidades

Em nossa jornada, exploramos como o Angular oferece uma proteção XSRF/CSRF robusta e personalizável. Se seu backend utiliza nomes diferentes para o cookie ou cabeçalho do token XSRF, você pode ajustá-lo facilmente para se adequar à sua configuração.

Configurando Nomes de Cookie e Cabeçalho Personalizados

A função withXsrfConfiguration permite personalizar os nomes do cookie e do cabeçalho XSRF. Basta adicioná-la à chamada provideHttpClient da seguinte forma:

export const appConfig: ApplicationConfig = {
  providers: [
    provideHttpClient(
      withXsrfConfiguration({
        cookieName: 'CUSTOM_XSRF_TOKEN',
        headerName: 'X-Custom-Xsrf-Header',
      }),
    ),
  ]
};

Nesse exemplo, o nome do cookie foi alterado para CUSTOM_XSRF_TOKEN e o nome do cabeçalho para X-Custom-Xsrf-Header. Essa flexibilidade garante que o Angular se adapte perfeitamente à sua configuração de backend.

Desabilitando a Proteção XSRF

Em algumas situações, o mecanismo de proteção XSRF integrado pode não ser adequado para sua aplicação. Nesses casos, você pode desativá-lo utilizando a função withNoXsrfProtection:

export const appConfig: ApplicationConfig = {
  providers: [
    provideHttpClient(
      withNoXsrfProtection(),
    ),
  ]
};

Ao desabilitar a proteção XSRF, você assume a responsabilidade de implementar seus próprios mecanismos de segurança para prevenir ataques CSRF. Essa decisão deve ser tomada com cuidado, após uma análise cuidadosa dos riscos e requisitos da sua aplicação.

Recursos Adicionais

Para aprofundar seu conhecimento sobre CSRF, recomendamos consultar os seguintes recursos:

Ao explorar esses recursos e utilizar as ferramentas de personalização do Angular, você estará equipado para construir aplicações mais seguras e resilientes a ataques CSRF.

Inclusão de Script Entre Sites (XSSI)

A inclusão de script entre sites, também conhecida como vulnerabilidade de JSON, pode permitir que o site de um atacante leia dados de uma API JSON. O ataque funciona em navegadores mais antigos ao substituir construtores de objetos JavaScript embutidos e, em seguida, incluir uma URL da API usando uma tag <script>.

Este ataque só é bem-sucedido se o JSON retornado for executável como JavaScript. Os servidores podem prevenir esse ataque prefixando todas as respostas JSON para torná-las não executáveis, usando a string bem conhecida ")]}',\n".

A biblioteca HttpClient do Angular reconhece essa convenção e automaticamente remove a string ")]}',\n" de todas as respostas antes de realizar a análise.

Exemplo de Proteção XSSI no Servidor

Para proteger sua API contra ataques XSSI, configure o servidor para prefixar todas as respostas JSON com a string ")]}',\n":

// Exemplo em Node.js com Express
app.get('/api/data', (req, res) => {
  const jsonData = { key: 'value' };
  res.set('Content-Type', 'application/json');
  res.send(`)]}',\n${JSON.stringify(jsonData)}`);
});

Como o Angular Lida com XSSI

O HttpClient do Angular remove automaticamente esse prefixo de todas as respostas antes de analisar o JSON. Isso garante que a resposta JSON seja segura para uso sem a necessidade de manipulações adicionais no lado do cliente.

Referência Adicional

Para mais informações, consulte a seção de XSSI deste post no blog de segurança da web do Google.

Auditoria de Aplicações Angular

As aplicações Angular devem seguir os mesmos princípios de segurança das aplicações web regulares e devem ser auditadas como tal. As APIs específicas do Angular que devem ser auditadas em uma revisão de segurança, como os métodos bypassSecurityTrust, são marcadas na documentação como sensíveis à segurança.

Recomendações para Auditoria de Segurança

  1. Revise o Uso de bypassSecurityTrust: Certifique-se de que os métodos bypassSecurityTrustHtml, bypassSecurityTrustScript, bypassSecurityTrustStyle, bypassSecurityTrustUrl e bypassSecurityTrustResourceUrl sejam usados com cautela e apenas quando necessário. Verifique se os valores marcados como confiáveis foram inspecionados e validados adequadamente.
  2. Sanitização de Dados: Garanta que todos os dados de entrada do usuário sejam validados e sanitizados antes de serem usados na aplicação. Utilize o DomSanitizer para garantir que os dados inseridos no DOM sejam seguros.
  3. Proteção XSRF/CSRF: Verifique se a proteção contra XSRF está corretamente configurada no cliente e no servidor. Assegure-se de que os tokens de autenticação são únicos por usuário e verificáveis pelo servidor.
  4. Configuração de CSP e Trusted Types: Implemente a Política de Segurança de Conteúdo (CSP) e configure Trusted Types para prevenir a execução de scripts maliciosos e impor práticas de codificação seguras.
  5. Interação Direta com o DOM: Minimize a interação direta com o DOM. Quando necessário, utilize as funções de sanitização do Angular para garantir a segurança dos dados.
  6. Prefixo XSSI em Respostas JSON: Certifique-se de que o servidor prefixa as respostas JSON com ")]}',\n" para proteger contra ataques de inclusão de script entre sites.

Conclusão

A segurança em aplicações Angular é multifacetada e requer atenção cuidadosa a vários aspectos, desde a sanitização de dados e proteção contra XSRF até a configuração de CSP e Trusted Types. Auditar regularmente sua aplicação e seguir as melhores práticas descritas aqui ajudará a garantir que sua aplicação Angular seja segura e robusta contra vulnerabilidades comuns da web.