Elastic Open Web Crawler como código
Aprenda a usar o GitHub Actions para gerenciar as configurações do Elastic Open Crawler, de forma que, sempre que enviarmos alterações para o repositório, elas sejam aplicadas automaticamente à instância implantada do crawler.
Com o Elastic Open Web Crawler e sua arquitetura orientada por linha de comando, ter configurações de crawler versionadas e um pipeline de CI/CD com testes locais agora é bastante simples de se obter.
Tradicionalmente, o gerenciamento de rastreadores era um processo manual e propenso a erros. Isso envolvia editar configurações diretamente na interface do usuário e ter dificuldades com a clonagem de configurações de rastreamento, reversão, controle de versão e muito mais. Tratar as configurações do rastreador como código resolve isso, proporcionando os mesmos benefícios que esperamos no desenvolvimento de software: repetibilidade, rastreabilidade e automação.
Esse fluxo de trabalho facilita a integração do Open Web Crawler ao seu pipeline de CI/CD para reversões, backups e migrações — tarefas que eram muito mais complicadas com versões anteriores do Elastic Crawler, como o Elastic Web Crawler ou o App Search Crawler.
Neste artigo, vamos aprender como:
Gerencie nossas configurações de rastreamento usando o GitHub.
Ter um ambiente local para testar pipelines antes da implantação.
Criar um ambiente de produção para executar o rastreador web com novas configurações sempre que enviarmos alterações para nossa branch principal.
Você pode encontrar o repositório do projeto aqui. No momento em que escrevo, estou usando o Elasticsearch 9.1.3 e o Open Web Crawler 0.4.2.
Pré-requisitos
Docker Desktop
instância do Elasticsearch
Máquina virtual com acesso SSH (por exemplo, AWS EC2) e Docker instalado.
Etapas
Estrutura de pastas
Configuração do rastreador
Arquivo Docker-compose (ambiente local)
Ações do GitHub
Testando localmente
Implantação em produção
Realizar alterações e redistribuir
Estrutura de pastas
Para este projeto, teremos a seguinte estrutura de arquivos:
├── docker-compose.yml # Local elasticsearch + crawler
├── config/crawler-config.yml # Crawler config
├── .github/workflows/deploy.yml # GH Action to deploy changes
├── local.sh # Script to run our local crawlerConfiguração do rastreador
Em crawler-config.yml, colocaremos o seguinte:
output_sink: elasticsearch
output_index: web-crawl-index
max_crawl_depth: 1
elasticsearch:
host: ${ES_HOST}
api_key: ${ES_API_KEY}
domains:
- url: https://web-scraping.dev
seed_urls:
- https://web-scraping.dev/product/1
- https://web-scraping.dev/product/2
- https://web-scraping.dev/product/3Este script irá extrair dados de https://web-scraping.dev/products, um site fictício para produtos. Iremos rastrear apenas as três primeiras páginas de produtos. A configuração max_crawl_depth impedirá que o rastreador descubra mais páginas do que as definidas como seed_urls , não abrindo os links dentro delas.
Elasticsearch host e api_key serão preenchidos dinamicamente dependendo do ambiente em que estamos executando o script.

Arquivo Docker-compose (ambiente local)
Para o ambiente local docker-compose.yml, implantaremos o rastreador e um único cluster Elasticsearch + Kibana, para que possamos visualizar facilmente os resultados do rastreamento antes da implantação em produção.
services:
es01:
image: docker.elastic.co/elasticsearch/elasticsearch:9.1.3
environment:
- discovery.type=single-node
- xpack.security.enabled=false
- ES_JAVA_OPTS=-Xms1g -Xmx1g
ports:
- "9200:9200"
networks: [esnet]
healthcheck:
test: ["CMD", "curl", "-f", "http://localhost:9200"]
interval: 5s
timeout: 5s
retries: 10
kibana:
image: docker.elastic.co/kibana/kibana:9.1.3
environment:
- ELASTICSEARCH_HOSTS=http://es01:9200
ports:
- "5601:5601"
networks: [esnet]
depends_on: [es01]
crawler:
image: docker.elastic.co/integrations/crawler:0.4.2
environment:
- ES_HOST=http://es01:9200
- CRAWLER_JRUBY_OPTS=--server
container_name: crawler
volumes:
- ./config:/home/app/config
networks: [esnet]
entrypoint: ["/home/app/bin/crawler", "crawl", "/home/app/config/crawl-config-final.yml"]
stdin_open: true
tty: true
networks:
esnet:
driver: bridgeObserve como o rastreador aguarda até que o Elasticsearch esteja pronto para ser executado.
Ações do GitHub
Agora precisamos criar uma ação do GitHub que copie as novas configurações e execute o rastreador em nossa máquina virtual a cada push para o repositório principal. Isso garante que sempre tenhamos a configuração mais recente implantada, sem precisar entrar manualmente na máquina virtual para atualizar arquivos e executar o rastreador. Vamos usar o AWS EC2 como provedor de máquinas virtuais.
O primeiro passo é adicionar o host (VM_HOST), o usuário da máquina (VM_USER), a chave SSH RSA (VM_KEY), o host do Elasticsearch (ES_HOST) e a chave da API do Elasticsearch (ES_API_KEY) aos segredos da ação do GitHub:

Dessa forma, a ação poderá acessar nosso servidor para copiar os novos arquivos e executar a indexação.
Agora, vamos criar nosso arquivo .github/workflows/deploy.yml :
name: Deploy
on:
push:
branches: [main]
jobs:
Deploy:
name: Deploy to EC2
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v5
- name: Deploy crawler
env:
HOSTNAME: ${{ secrets.VM_HOST }}
USER_NAME: ${{ secrets.VM_USER }}
PRIVATE_KEY: ${{ secrets.VM_KEY }}
ES_HOST: ${{ secrets.ES_HOST }}
ES_API_KEY: ${{ secrets.ES_API_KEY }}
run: |
# Save private key
echo "$PRIVATE_KEY" > private_key
chmod 600 private_key
# Generate final config locally
envsubst < config/crawler-config.yml > config/crawl-config-final.yml
# Copy the config folder to VM
scp -o StrictHostKeyChecking=no -i private_key -r config ${USER_NAME}@${HOSTNAME}:~/config
# SSH into VM and run crawler
ssh -o StrictHostKeyChecking=no -i private_key ${USER_NAME}@${HOSTNAME} << EOF
docker run --rm \
-v ~/config:/config \
docker.elastic.co/integrations/crawler:latest jruby \
bin/crawler crawl /config/crawl-config-final.yml
EOFEssa ação executará os seguintes passos sempre que enviarmos alterações para o arquivo de configuração do rastreador:
Preencha o arquivo de configuração YAML com o host e a chave da API do Elasticsearch.
Copie a pasta de configuração para a nossa máquina virtual.
Conecte-se à nossa VM via SSH.
Execute o rastreamento com a configuração que acabamos de copiar do repositório.
Testando localmente
Para testar nosso rastreador localmente, criamos um script bash que popula o host do Elasticsearch com a versão local do Docker e inicia uma busca. Você pode executar ./local.sh para executá-lo.
#!/bin/bash
# Exit on any error
set -e
# Load environment variables
export ES_HOST="http://es01:9200"
# Generate final crawler config
envsubst < ./config/crawler-config.yml > ./config/crawl-config-final.yml
# Bring everything up
docker compose up --buildVamos verificar as Ferramentas de Desenvolvedor do Kibana para confirmar se o campo web-crawler-index foi preenchido corretamente:

Implantação em produção
Agora estamos prontos para enviar a alteração para a branch principal, o que implantará o crawler em sua máquina virtual e começará a enviar logs para sua instância do Elasticsearch Serverless.
git add .
git commit -m "First commit"
git pushIsso acionará a ação do GitHub, que executará o script de implantação na máquina virtual e iniciará a indexação.
Você pode confirmar se a ação foi executada acessando o repositório do GitHub e visitando a aba “Ações”:

Realizar alterações e redistribuir
Algo que você pode ter notado é que o price de cada produto faz parte do corpo do documento. O ideal seria armazenar o preço em um campo separado para que pudéssemos aplicar filtros a ele.
Vamos adicionar essa alteração ao arquivo crawler.yml para usar regras de extração para extrair o preço da classe CSS product-price :
output_sink: elasticsearch
output_index: web-crawl-index
max_crawl_depth: 1
elasticsearch:
host: ${ES_HOST}
api_key: ${ES_API_KEY}
# Index ingest pipeline to process documents before indexing
pipeline_enabled: true
pipeline: pricing-pipeline
domains:
- url: https://web-scraping.dev
seed_urls:
- https://web-scraping.dev/product/1
- https://web-scraping.dev/product/2
- https://web-scraping.dev/product/3
extraction_rulesets:
- url_filters:
- type: ends
pattern: /product/*
rules:
- action: extract
field_name: price
selector: .product-price
join_as: string
source: htmlTambém vemos que o preço inclui um sinal de dólar ($), que devemos remover se quisermos executar consultas de intervalo. Podemos usar um pipeline de ingestão para isso. Observe que estamos fazendo referência a ele em nosso novo arquivo de configuração do rastreador acima:
PUT _ingest/pipeline/pricing-pipeline
{
"processors": [
{
"script": {
"source": """
ctx['price'] = ctx['price'].replace("$","")
"""
}
}
]
}Podemos executar esse comando em nosso cluster Elasticsearch de produção. Para o desenvolvimento, como é efêmero, podemos fazer com que a criação do pipeline faça parte do arquivo docker-compose.yml adicionando o seguinte serviço. Observe que também adicionamos um depends_on ao serviço de rastreamento para que ele seja iniciado após a criação bem-sucedida do pipeline.
crawler:
image: docker.elastic.co/integrations/crawler:0.4.2
environment:
- ES_HOST=http://es01:9200
- CRAWLER_JRUBY_OPTS=--server
container_name: crawler
volumes:
- ./config:/home/app/config
networks: [esnet]
entrypoint: ["/home/app/bin/crawler", "crawl", "/home/app/config/crawl-config-final.yml"]
depends_on:
pipeline-init:
condition: service_completed_successfully
stdin_open: true
tty: true
pipeline-init:
image: curlimages/curl:latest
depends_on:
es01:
condition: service_healthy
networks: [esnet]
entrypoint: >
sh -c "
echo 'Creating ingest pipeline...';
curl -s -X PUT http://es01:9200/_ingest/pipeline/pricing-pipeline \\
-H 'Content-Type: application/json' \\
-d '{\"processors\":[{\"script\":{\"source\":\"ctx.price = ctx.price.replace(\\\"$\\\", \\\"\\\")\"}}]}';
echo 'Pipeline created!';
"Agora vamos executar `./local.sh` para ver a alteração localmente:

Ótimo! Agora vamos impulsionar a mudança:
git add crawler-config.yml
git commit -m "added price CSS selector"
git pushPara confirmar se tudo funciona corretamente, você pode verificar seu Kibana de produção, que deverá refletir as alterações e mostrar o preço como um novo campo sem o símbolo de dólar.
Conclusão
O Elastic Open Web Crawler permite que você gerencie seu crawler como código, o que significa que você pode automatizar todo o pipeline — do desenvolvimento à implantação — e adicionar ambientes locais efêmeros e testes com os dados rastreados programaticamente, para citar alguns exemplos.
Você está convidado a clonar o repositório oficial e começar a indexar seus próprios dados usando este fluxo de trabalho. Você também pode ler este artigo para aprender como executar uma pesquisa semântica em índices produzidos pelo rastreador.




