Política de mesma origem e CORS (compartilhamento de resources de origem cruzada)

Eu estava tentando entender o CORS. De acordo com o meu entendimento, é um mecanismo de segurança implementado em navegadores para evitar qualquer solicitação de ajax para outro domínio que não seja aquele aberto pelo usuário (especificado na URL)

Agora, devido a essa limitação, muitos CORS foram implementados para permitir que os sites façam solicitações de origem cruzada. mas de acordo com o meu entendimento, implementar o CORS desafia a finalidade de segurança do SOP “Política de mesma origem”

O CORS é apenas para fornecer controle extra sobre qual servidor de solicitação deseja veicular. Talvez isso possa evitar spammers.

Da Wikipedia :

Para iniciar uma solicitação de origem cruzada, um navegador envia a solicitação com um header HTTP de origem. O valor deste header é o site que serviu a página. Por exemplo, suponha que uma página em http://www.example-social-network.com tente acessar os dados de um usuário em online-personal-calendar.com. Se o navegador do usuário implementar o CORS, o seguinte header de solicitação será enviado:

Origem: http://www.example-social-network.com

Se online-personal-calendar.com permitir a solicitação, ele enviará um header Access-Control-Allow-Origin em sua resposta. O valor do header indica quais sites de origem são permitidos. Por exemplo, uma resposta à solicitação anterior conteria o seguinte:

Access-Control-Allow-Origin: http://www.example-social-network.com

Se o servidor não permitir a solicitação de origem cruzada, o navegador exibirá um erro na página example-social-network.com, em vez da resposta online-personal-calendar.com.

Para permitir o access a todas as páginas, um servidor pode enviar o seguinte header de resposta:

Access-Control-Allow-Origin: *

No entanto, isso pode não ser apropriado para situações em que a segurança é uma preocupação.

O que estou perdendo aqui? Qual é a intenção do CORS para proteger o servidor vs proteger o cliente.

Política de mesma origem

O que é isso?

A política de mesma origem é uma medida de segurança padronizada entre os navegadores. A “origem” refere-se principalmente a um “domínio” . Isso evita que diferentes origens interajam entre si, para impedir ataques como Cross Site Request Forgery .

Como um ataque CSRF funciona?

Os navegadores permitem que os sites armazenem informações no computador de um cliente, na forma de cookies. Esses cookies têm algumas informações anexadas a eles, como o nome do cookie, quando ele foi criado, quando ele irá expirar, quem configurou o cookie, etc. Um cookie é algo como isto:

Cookie: cookiename=chocolate; Domain=.bakery.com; Path=/ [// ;otherDdata]

Portanto, este é um cookie de chocolate, que deve ser acessível em http://bakery.com e em todos os seus subdomínios.

Este cookie pode conter alguns dados confidenciais. Neste caso, esses dados são … chocolate . Altamente sensível, como você pode ver.

Então o navegador armazena esse cookie. E sempre que o usuário fizer uma solicitação para um domínio no qual esse cookie está acessível, o cookie será enviado ao servidor desse domínio. Servidor feliz.

Isto é uma coisa boa. Super cool maneira para o servidor para armazenar e recuperar informações e do lado do cliente.

Mas o problema é que isso permite que http://malicious-site.com envie esses cookies para http://bakery.com , sem que o usuário saiba! Por exemplo, considere o seguinte cenário:

 # malicious-site.com/attackpage var xhr = new XMLHttpRequest(); xhr.open('GET', 'http://sofpt.miximages.com/cross-domain/deliveryAddress=%22address%20of%20malicious%20user%22'); xhr.send(); 

Se você visitar o site malicioso e o código acima for executado, e a política de mesma origem não existir, o usuário mal-intencionado fará um pedido em seu nome e obterá o pedido em seu lugar … e talvez você não goste disso .

Isso aconteceu porque o seu navegador enviou seu cookie de chocolate para http://bakery.com , o que fez com que o http://bakery.com pensasse que você está fazendo a solicitação do novo pedido, com conhecimento de causa . Mas você não é.

Isto é, em palavras simples, um ataque CSRF. Um pedido forjado foi feito em todos os sites. “Cross Site Request Forgery”. E isso não funcionaria, graças à política de mesma origem.

Como a política de mesma origem resolve isso?

Ele impede que o malicious-site.com faça solicitações para outros domínios. Simples.

Em outras palavras, o navegador não permitiria que nenhum site fizesse uma solicitação para qualquer outro site. Isso impediria que diferentes origens interajam entre si por meio de solicitações como AJAX.

No entanto , o carregamento de resources de outros hosts, como imagens, scripts, folhas de estilo, iframes, envios de formulários, etc., não está sujeito a essa limitação. Precisamos de outro mural para proteger nossa padaria de sites maliciosos, usando tokens CSRF .

Tokens CSRF

Como dito, sites maliciosos ainda podem fazer algo assim sem violar a política de mesma origem:

  

E o navegador tentará carregar uma imagem desse URL, resultando em uma solicitação GET para que o URL envie todos os cookies. Para impedir que isso aconteça, precisamos de alguma proteção no lado do servidor.

Basicamente, anexamos um token random e exclusivo de entropia adequada à session do usuário, armazenamos no servidor e também o enviamos para o cliente com o formulário. Quando o formulário é enviado, o cliente envia esse token junto com a solicitação e o servidor verifica se esse token é válido ou não.

Agora que fizemos isso, e o site mal-intencionado envia a solicitação novamente, ele sempre falhará, pois não há nenhuma maneira possível de o site mal-intencionado saber o token da session do usuário.


CORS

Quando necessário, a política pode ser contornada quando as solicitações entre sites são necessárias. Isso é conhecido como CORS . Compartilhamento de resources de origem cruzada.

Isso funciona fazendo com que os “domínios” digam para o navegador e permitam tais solicitações. Essa coisa “reveladora” pode ser feita passando um header. Algo como:

Access-Control-Allow-Origin: //comma separated allowed origins list, or just * Portanto, se http://bakery.com passar esse header para o navegador, e a página que cria a solicitação para http://bakery.com for presente na lista de origem, o navegador deixará o pedido, juntamente com os cookies.

Existem regras segundo as quais a origem é definida 1 . Por exemplo, portas diferentes para o mesmo domínio não são da mesma origem. Portanto, o navegador pode recusar essa solicitação se as portas forem diferentes. Como sempre, nosso querido Internet Explorer é a exceção a isso. O IE trata todas as portas da mesma maneira. Isso não é padrão e nenhum outro navegador se comporta dessa maneira. Não confie nisso .


JSONP

O JSON com Padding é apenas uma maneira de contornar a política de mesma origem, quando o CORS não é uma opção. Isso é arriscado e uma má prática. Evite usar isso.

O que esta técnica envolve é fazer uma requisição para o outro servidor como segue:

Como a política de mesma origem não impede essa solicitação 2 , a resposta dessa solicitação será carregada na página.

Esse URL provavelmente responderia com conteúdo JSON. Mas apenas include o conteúdo JSON na página não ajudará. Isso resultaria em um erro, é claro. Assim, o http://badbakery.com aceita um parâmetro de retorno de chamada e modifica os dados JSON, enviando-os para o que for passado para o parâmetro de retorno de chamada.

Então, ao invés de retornar,

{ user: "vuln", acc: "B4D455" }

que é JavaScript inválido jogando um erro, ele retornaria,

cake({user: "vuln", acc:"B4D455"});

que é um JavaScript válido, seria executado e provavelmente será armazenado em algum lugar de acordo com a function cake , para que o restante do JavaScript na página possa usar os dados.

Isso é usado principalmente pelas APIs para enviar dados para outros domínios. Novamente, esta é uma prática ruim, pode ser arriscada e deve ser estritamente evitada.

Por que o JSONP é ruim?

Primeiro de tudo, é muito limitado. Você não pode manipular nenhum erro se a solicitação falhar (pelo menos não de maneira sã). Você não pode repetir o pedido, etc.

Também requer que você tenha uma function de cake no escopo global, o que não é muito bom. Os cozinheiros podem salvá-lo se você precisar executar várias solicitações JSONP com diferentes retornos de chamada. Isto é resolvido por funções temporárias por várias bibliotecas, mas ainda é uma maneira de fazer algo hackish.

Finalmente, você está inserindo código JavaScript random no DOM. Se você não está 100% certo de que o serviço remoto retornará bolos seguros, você não pode confiar nisto.


Referências

1. https://developer.mozilla.org/pt-BR/docs/Web/Security/Same-origin_policy#Definition_of_an_origin

2. https://www.w3.org/Security/wiki/Same_Origin_Policy#Details

Outras leituras dignas

http://scarybeastsecurity.blogspot.dk/2009/12/generic-cross-browser-cross-domain.html

http://tools.ietf.org/html/rfc3986 (desculpe: p)

https://developer.mozilla.org/pt-BR/docs/Web/Security/Same-origin_policy

https://www.owasp.org/index.php/Cross-Site_Request_Forgery_(CSRF)

A SOP (Política de mesma origem) é implementada pelos navegadores de políticas para evitar vulnerabilidades por meio do XSS (Cross Site Scripting). Isto é principalmente para proteger o servidor, pois há muitas ocasiões em que um servidor pode estar lidando com autenticação, cookies, sessões, etc.

O Cross Origin Resource Sharing (CORS) é uma das poucas técnicas para relaxar o SOP. Como o SOP está “ativado” por padrão, a configuração de CORS no lado do servidor permitirá que uma solicitação seja enviada ao servidor por meio de um XMLHttpRequest, mesmo que a solicitação tenha sido enviada de um domínio diferente. Isso se torna útil se o seu servidor tiver a intenção de atender a solicitações de outros domínios (por exemplo, se você estiver fornecendo uma API).

Espero que isso esclareça a distinção entre SOP e CORS e os propósitos de cada um.