Como validar URLs com segurança em Python
Afzaal Ahmad Zeeshan
4 de novembro de 2022
0 minutos de leituraTudo na internet tem um Localizador Uniforme de Recursos (URL) que o identifica exclusivamente e permite que as pessoas acessem arquivos e outras mídias. Por exemplo, este artigo tem uma URL exclusiva que ajuda os rastreadores de otimização para mecanismos de busca (SEO) a indexá-lo para que as pessoas o encontrem.
A primeira definição da sintaxe de URL aparece no Request for Comments (RFC) 1738, de 1994. Desde então, a estrutura das URLs passou por várias revisões para melhorar sua segurança. No entanto, muitas vezes os desenvolvedores não seguem a definição do RFC como previsto, o que contribui para diversos ataques maliciosos.
Um exemplo recente é a exploração de dia zero para execução remota de código (RCE) encontrada no Log4j, um pacote popular de registro de logs em Java. O ataque ocorreu quando a Interface de Nomes e Diretórios Java (JNDI) avaliou uma string de log maliciosa. A JNDI é uma API Java para serviços de diretório que permite que clientes de software Java descubram e consultem dados e recursos (na forma de objetos Java) usando um nome. Ao avaliar uma string de log maliciosa, ela se conecta a um servidor remoto e executa código Java malicioso. Por isso, as empresas precisam validar continuamente as URLs fornecidas por agentes externos, como clientes, parceiros e outros.
Outro exemplo é o ataque de falsificação de requisição do lado do servidor, que pode comprometer um programa de servidor quando ele acessa uma URL insegura. Pessoas mal-intencionadas podem explorar os campos de entrada fornecidos para causar danos às nossas soluções web — e, pior ainda, à imagem pública da nossa organização.
Neste artigo, vamos explorar os desafios causados por URLs corrompidas, como elas podem prejudicar suas aplicações e como lidar com esse problema. Para acompanhar, verifique se o Python está instalado e configurado na sua máquina.
Riscos de segurança relacionados a URLs
As URLs podem ser arriscadas, pois podem redirecionar as pessoas de uma página legítima para uma página maliciosa. Elas também podem abrir vários vetores de ataque, incluindo cross-site scripting (XSS), uma vulnerabilidade de segurança presente em algumas aplicações web. A vulnerabilidade XSS permite que invasores injetem scripts do lado do cliente em páginas web visualizadas por outras pessoas.
Esse risco de segurança pode ter consequências graves em setores específicos, como o bancário. Um cliente desavisado pode abrir uma página aparentemente legítima, controlada por um invasor, por acreditar que se trata da página de login do aplicativo do banco. Esse é um tipo de ataque de phishing baseado em engenharia social, no qual um invasor envia mensagens fraudulentas, falsas ou enganosas para induzir alguém a revelar informações confidenciais. O invasor também pode instalar softwares maliciosos na infraestrutura da vítima, incluindo ransomware. Se conseguir obter o nome de usuário e a senha de alguém que usa o banco, poderá acessar a conta dessa pessoa e causar danos.
Ataques mais avançados envolvendo URLs podem ocorrer por meio da falsificação de requisição do lado do servidor. Esse ataque acontece em servidores que enviam requisições às URLs fornecidas pelos clientes. Ao fazer uma requisição, um invasor pode assumir o controle do servidor para executar ações não autorizadas, como verificar portas e informações de rede, solicitar metadados da infraestrutura, imprimir dados e exibir informações confidenciais, como senhas ou tokens.
Nas próximas seções, você vai ver como validar e higienizar URLs que não controla. Por exemplo, se estivermos criando uma plataforma social onde as pessoas podem se comunicar e compartilhar dados, podemos controlar quais URLs são permitidas e quais podemos ocultar.
Como validar URLs em Python
Python é uma linguagem de programação amplamente usada para criar aplicações e sites para milhões de clientes em todo o mundo. Embora não tenha um verificador e validador de URLs integrado, o Python conta com analisadores e validadores de URL desenvolvidos pela comunidade, que podem ser usados para validar e tornar nossas URLs mais seguras. Alguns frameworks de aplicações web também oferecem verificadores e validadores de URL para o desenvolvimento dessas aplicações.
Validando URLs
Um método popular para validar URLs em Python é o pacote validators. Podemos usá-lo para verificar se uma URL é válida. Para ser válida, uma URL precisa:
Estar bem formada, ou seja, seguir todas as regras das especificações HTTP ou HTTPS
Ter um recurso nesse endereço, pois a URL é inválida sem um recurso associado
O pacote Python validators disponibiliza um método para verificar a URL, conferir se ela é segura e procurar palavras-chave e caracteres inválidos. Se a URL estiver disponível no domínio público (ou seja, não estiver protegida por firewall, paywall ou outra barreira de acesso), o pacote ignora endereços IP internos.
Para usar o pacote validators, baixe e configure a dependência no ambiente Python local usando o pip. Para baixar o pacote validators, execute o código a seguir no terminal ou na interface de linha de comando local:
Quando o comando terminar, o pacote validators estará na nossa máquina.
Em seguida, crie um arquivo Python chamado main.py e escreva o código para testar uma URL:
Depois de adicionar esse código ao arquivo main.py, execute-o no interpretador Python usando a interface de linha de comando do Python:
O código exibe "URL is invalid" porque falta o caractere / na URL depois de http:/.
O pacote também pode determinar se uma URL está acessível publicamente, o que ajuda a verificar se a pessoa está tentando acessar um endereço IP interno. Adicione o código a seguir ao mesmo arquivo e execute-o para testar a validação de uma URL.
Mais uma vez, a saída informa que a URL é inválida. Isso acontece porque ela não está disponível em domínios públicos, embora não haja nenhum problema com a URL em si. Para saber mais sobre os recursos do pacote validators, consulte a documentação.
Análise com expressões regulares
Outra abordagem para validar URLs é usar expressões regulares. Por exemplo, podemos exigir que uma URL inclua HTTPS para que seja validada. O código para fazer essa validação é:
Essa expressão regular corresponde ao termo https://www.google.com, mas não a http://www.google.com, embora ambas sejam URLs válidas. Saiba mais sobre expressões regulares neste site. Também podemos testar a expressão acima em código Python:
O código acima exibe a URL correspondente. Se você alterar a string da URL acima e remover o HTTPS ou usar HTTP, receberá um objeto None, indicando que não houve correspondência.
No entanto, expressões regulares são complexas e pouco práticas em situações reais. São difíceis de ler, depurar e ampliar. Por isso, as bibliotecas geralmente são uma opção melhor.
Para ver um caso de uso mais avançado de expressão regular que analisa a URL com todas as estruturas e sintaxes válidas, confira esta discussão no Stack Overflow.
Uma vantagem de usar expressões regulares é que elas também permitem encontrar URLs inválidas em strings de entrada. Isso só é possível com expressões regulares, não com bibliotecas comuns. O pacote validators não funciona quando a string contém espaços em branco no início ou no fim. Para usar o pacote da melhor forma, você precisa higienizar a string de entrada e passá-la ao validators.
Usando urllib
Outro pacote que analisa a URL e disponibiliza suas partes é o urllib. Podemos usá-lo com o interpretador Python 3.
O código a seguir verifica se uma URL é válida:
Quando definimos o esquema e o campo netloc para a variável result, a URL é válida e pode ser usada. Caso contrário, ela é inválida e devemos ter cautela.
Identificando vulnerabilidades comuns
Alguns frameworks Python, como o Django, oferecem pacotes validadores integrados que permitem validar URLs nesse framework. No entanto, confiar nessas bibliotecas traz um desafio: mesmo que conheçamos bem o framework, ainda precisamos garantir que o próprio pacote seja seguro. E o código aberto torna ainda mais complexa a tarefa de confiar no pacote.
Podemos usar uma ferramenta de segurança como o Snyk Advisor para analisar rapidamente todos os pacotes de código aberto que usamos — e os novos que queremos implementar — em busca de vulnerabilidades comuns. Com essa análise, a Snyk fornece um relatório de segurança que podemos usar para decidir se devemos incluir o pacote. Por exemplo, podemos usar o Snyk Advisor para garantir que nossos pacotes, como o pacote validators usado na demonstração acima, sejam seguros.
Também podemos usar o Snyk Open Source com o Snyk Advisor para identificar problemas de licenciamento, vulnerabilidades e outras questões de segurança que possam existir na nossa stack de ferramentas de código aberto. Além disso, podemos consultar o Snyk Vulnerability Database (VulnDB) para pesquisar vulnerabilidades conhecidas relacionadas a URLs, como esta vulnerabilidade no framework Flask, que redireciona uma pessoa para um local sem validar a URL. Consultando esse banco de dados, podemos proteger proativamente nossas páginas web e aplicações.
Validando URLs em Python
Neste artigo, exploramos os desafios que URLs não higienizadas trazem para uma aplicação web e como higienizá-las conforme necessário. Começamos com validações básicas usando os pacotes validator e urllib. Também mostramos como usá-los para confirmar se todas as URLs são públicas ou se algumas são URLs internas usadas para atacar a aplicação web. Em seguida, usamos uma expressão regular básica para mostrar como uma linha de código pode verificar informações essenciais nas URLs, como o uso de HTTPS em todas elas. Também explicamos por que as expressões regulares são uma forma complexa e desafiadora de validar URLs.
Por fim, vimos como escolher bibliotecas de código aberto seguras. O Snyk Advisor é uma fonte confiável de informações para quem usa pacotes de código aberto. Para saber mais, consulte o guia de boas práticas de segurança em Python e prepare seus pipelines de integração e entrega contínuas (CI/CD) para analisar qualquer vulnerabilidade adicionada ao seu código.
Comece a resolver desafios de capture the flag
Aprenda a resolver desafios de capture the flag assistindo sob demanda ao nosso workshop virtual introdutório.



