DEV Community

Natália Oliveira
Natália Oliveira

Posted on • Edited on

Infraestrutura para análise de dados com Jupyter, Cassandra, Pyspark e Docker

jupyter-notebook


Imagem retirada do site do Jupyter Notebooks


Texto originalmente publicado aqui.


Hoje vou mostrar como configurar um projeto para análise de dados com o Cassandra e o Jupyter Notebook com Pyspark, usando tudo no Docker. Vamos abordar:

Antes de começar, essa é a estrutura de pastas do projetinho:

cassandra-jupyter-spark-python
├── .gitignore
├── Makefile
├── README.md
├── data
│   └── csv-here.md
├── docker-compose.yml
├── jupyter
│   └── Untitled.ipynb
└── pyproject.toml
Enter fullscreen mode Exit fullscreen mode

Você pode encontrar um projeto similiar a esse, completo, com análise de dados (porcamente feita por mim) no GitHub.

Configurando o Apache Cassandra com Docker

O Cassandra é um banco de dados NoSQL decentralizado, com escalabilidade elástica, altamente disponível, tolerante a falhas e orientado a linhas particionadas; escrevi um texto sobre o Cassandra aqui e você pode verificar a documentação do Cassandra aqui.

Para subir o Cassandra com Docker podemos fazer o seguinte:

services:
  cassandra1:
    image: cassandra:4.0.14
    container_name: cassandra1
    networks:
      - cassandra_network
    environment:
      - CASSANDRA_CLUSTER_NAME=cassandra_cluster
      - CASSANDRA_SEEDS=cassandra1
      - CASSANDRA_DC=datacenter1
      - CASSANDRA_RACK=rack1
      - CASSANDRA_ENDPOINT_SNITCH=GossipingPropertyFileSnitch
    volumes:
      - ./data:/data
    ports:
      - "9042:9042"
Enter fullscreen mode Exit fullscreen mode

No código acima estamos criando um node do Cassandra 4.0.14 (versão escolhida para evitar problemas de compatibilidade nesse projeto) numa rede Docker chamada cassandra_network. Explicando as variáveis de ambiente no environment:

  • CASSANDRA_CLUSTER_NAME: define o nome do cluster onde um ou mais nodes do Cassandra irão rodar. Cluster se refere a mais de uma máquina, geralmente para se referir a um sistema distribuído. No “docker-compose” do projeto chamamos de “cassandra_cluster”;
  • CASSANDRA_SEEDS: indica os serviços (ou IPs) usados pelo gossip do Cassandra, para adicionar novos nodes ao cluster. O gossip é um protocolo utilizado para manter informações sobre o status dos nodes no cluster, para dar suporte a descentralização e tolerância a particionamento;
  • CASSANDRA_DC: define o data center do node, que é um agrupamento lógico de racks. Não é necessário para rodar essa infraestrutura localmente em um notebook, como é o caso atual, mas seria utilizado caso estivéssemos utilizando o Cassandra com o uso adequado a que se propõe;
  • CASSANDRA_RACK: define o rack do node, que é um agrupamento lógico de nodes. Novamente, não é necessário para a situação atual, mas seria utilizado em um caso real;
  • CASSANDRA_ENDPOINT_SNITCH: define a implementação de snitch que esse node irá utilizar. O snitch provê informações sobre a topologia da rede onde o Cassandra está para redirecionar requisições de forma mais eficiente. Nesse caso aqui configuramos como “GossipingPropertyFileSnitch”, geralmente usado em produção, para considerar as informações de rack e datacenter.

O volume ./data:/data serve para que você coloque, por exemplo, arquivos .csv parte da sua análise de dados. No meu caso, criei um projeto para a pós-graduação, onde usei o comando COPY para repassar os dados tratados do .csv para o Cassandra.

Agora, criando um segundo node Cassandra:

cassandra2:
  image: cassandra:4.0.14
  container_name: cassandra2
  networks:
    - cassandra_network
  environment:
    - CASSANDRA_CLUSTER_NAME=cassandra_cluster
    - CASSANDRA_SEEDS=cassandra1
    - CASSANDRA_DC=datacenter1
    - CASSANDRA_RACK=rack1
    - CASSANDRA_ENDPOINT_SNITCH=GossipingPropertyFileSnitch
  volumes:
    - ./data:/data
  ports:
    - "9043:9042"
  depends_on:
    - cassandra1
Enter fullscreen mode Exit fullscreen mode

Você pode usar somente um node, já que está rodando em seu computador, mas vale lembrar que um node só perde o propósito de uso do Cassandra. Esse banco é feito para ter diversos nodes no cluster.

Veja que esse segundo node aponta os seeds para o outro node. Isso é para que o cassandra2 se conecte com o cassandra1, para descrobrir a topologia do cluster e se unir a esse cluster.

O que é o Spark?

O Apache Spark é uma engine para engenharia e análise de dados, ciência de dados e machine learning em larga escala, onde é possível rodar para máquinas com um único nó ou cluster. Podemos usar Python, SQL, Scala, Java e R para interagir com o Spark, e aqui nesse projeto usaremos Python, com Pyspark.

Usos do Spark, segundo sua documentação:

  • Batch/streaming: unifica o processamento dos dados em lotes e streaming em tempo real, usando Python, SQL, Scala, Java ou R
  • Análise de SQL: executa consultas ANSI SQL rápidas e distribuídas para painéis e relatórios ad-hoc
  • Ciência de dados em escala: executa Análise Exploratória de Dados (EDA) em dados em escala de petabytes sem precisar recorrer à redução de amostragem
  • Aprendizado de máquina: treine algoritmos de aprendizado de máquina em um laptop e use o mesmo código para escalar para clusters tolerantes a falhas de milhares de máquinas.

Configurando o Jupyter com Pyspark no Docker

O Jupyter é uma tecnologia para computação interativa onde usamos uma linguagem de programação para, geralmente, fazer análises de dados e experimentos do tipo. Para rodá-lo no Docker:

  # Docker Hub Image. Uses spark-3.5.0-bin-hadoop3
  jupyter_pyspark:
    image: jupyter/pyspark-notebook:latest
    container_name: juptyer_pyspark
    environment:
      JUPYTER_ENABLE_LAB: "yes"
    ports:
      - "8888:8888"
    networks:
      - cassandra_network
    volumes:
      - ./jupyter:/home/jovyan
    depends_on:
      - cassandra1

networks:
  cassandra_network:
    driver: bridge
Enter fullscreen mode Exit fullscreen mode

Essa imagem do Jupyter já vem com o Spark, mas vale apontar que aqui estamos usando a imagem do Docker Hub, que não recebe atualizações e está parada no Spark 3.5.0 e Hadoop 3, e não da Quay, que recebe atualizações. Tive muitos problemas tentando manter a compatibilidade entre as ferramentas, e a imagem do Docker Hub funcionou para o propósito.

O volume, assim como nos cassandras, é para poder salvar os notebooks no host. O container está na mesma rede que os outros e o JUPYTER_ENABLE_LAB é para que a gente não precise fazer login ou usar token, bastará abrir o browser no http://localhost:8888:

jupyter

Iniciando uma sessão Spark conectada no Cassandra

Com o docker-compose.yml finalizado, podemos rodar os containers:

docker compose up --build
Enter fullscreen mode Exit fullscreen mode

No http://localhost:8888, abrindo um novo arquivo no Jupyter, vamos importar uma sessão Spark da lib pyspark:

from pyspark.sql import SparkSession
Enter fullscreen mode Exit fullscreen mode

E configurar a sessão:

spark = SparkSession.builder.appName("test").config("spark.jars.packages", "com.datastax.spark:spark-cassandra-connector_2.12:3.5.0").config("spark.cassandra.connection.host", "cassandra1").config("spark.cassandra.connection.port", "9042").getOrCreate()
Enter fullscreen mode Exit fullscreen mode

Muita atenção aqui nessa parte. O código acima está:

  • Iniciando uma sessão Spark
  • Criando um novo "app" (o projeto em si) chamado "test"
  • Configurando o Spark com um pacote jar, utilizando um conector de Spark para Cassandra
  • Conectando com o serviço Cassandra chamado cassandra1
  • Configurando a porta da conexão para o 9042, que é onde está nosso container
  • Criando a conexão

Note que estamos usando um conector específico:

spark-cassandra-connector_2.12:3.5.0
Enter fullscreen mode Exit fullscreen mode

Podemos olhar essas versões no site do Maven, e aqui nesse ponto foi onde mais topei com erros, especialmente de compatibilidade.

Se tudo der certo no comando anterior, depois rode esse comando para ver a sessão
ativa:

spark.active()
Enter fullscreen mode Exit fullscreen mode

Você verá algo assim:

jupyter-pyspark


Fontes:

Imagem Docker do Cassandra

Image Docker do Jupyter com Spark

Apache Spark

Billboard image

Use Playwright to test. Use Playwright to monitor.

Join Vercel, CrowdStrike, and thousands of other teams that run end-to-end monitors on Checkly's programmable monitoring platform.

Get started now!

Top comments (0)

A Workflow Copilot. Tailored to You.

Pieces.app image

Our desktop app, with its intelligent copilot, streamlines coding by generating snippets, extracting code from screenshots, and accelerating problem-solving.

Read the docs

👋 Kindness is contagious

Engage with a sea of insights in this enlightening article, highly esteemed within the encouraging DEV Community. Programmers of every skill level are invited to participate and enrich our shared knowledge.

A simple "thank you" can uplift someone's spirits. Express your appreciation in the comments section!

On DEV, sharing knowledge smooths our journey and strengthens our community bonds. Found this useful? A brief thank you to the author can mean a lot.

Okay