Olá Mundo

Se hoje é possível criar um site com um prompt, por que eu criei o meu site do zero?

Introdução

Ainda me lembro da sensação de ter criado o meu primeiro site. Não era fácil criar um site nos anos 90, mas eu tinha o privilégio de ter um computador com Internet em casa, então eu aproveitei a oportunidade.

Eu comecei estudando as tecnologias necessárias usando revistas sobre o assunto. Aprendi sobre HTML, HTTP, FTP, DNS e como instalar e usar o FrontPage. Criei as páginas, copiei os arquivos via FTP para os servidores da GeoCities e consegui um endereço DNS. O site estava publicado e eu me senti realizado.

Hoje é possível criar um site com um prompt. Em alguns minutos um site completo pode ser criado e publicado na Internet. No entanto, como desenvolvedor, eu gosto de criar, publicar e entender como as coisas funcionam. Por isso decidi criar o meu site do zero.

Esse artigo conta como foi o processo.

Objetivo

Este site é um projeto que faz parte do meu objetivo de criar uma marca profissional e compartilhar conhecimento com outras pessoas. Eu me inspirei em sites de pessoas que sigo, como a Julia Evans, Will Larson e Kent Beck. Este site também foi uma desculpa para desenvolver e aprender tecnologias novas.

Ferramentas

Usei ferramentas de IA em todo o processo. A stack que usei foi:

  • Gemini, no plano Google AI Pro.
  • Stitch, como gerador de ideias de design.
  • Antigravity, como agente de desenvolvimento síncrono.
  • Jules, como agente de desenvolvimento assíncrono.

Em um artigo futuro vou compartilhar mais sobre a minha stack de ferramentas de inteligência artificial.

Com as ferramentas definidas, segui para o projeto.

Projeto

Comecei criando um notebook no Gemini para organizar as minhas referências, prompts e documentos. Adicionei alguns sites de referência e gerei alguns documentos com ideias de conteúdo.

Com o projeto organizado, segui para o design.

Design

Usei o Stitch para gerar algumas ideias de design para o site. Usei os documentos gerados na etapa anterior para ajudar no contexto. Depois de alguns minutos já tinha uma boa ideia do estilo e arquitetura da informação.

Com o design idealizado, segui para o repositório.

Repositório

Criei um repositório para organizar o código-fonte. Usei um monorepo, para garantir que as dependências entre as especificações, o site e a infraestrutura ficassem bem definidas.

Usei esta estrutura de arquivos e diretórios:

moyle-dev/      # Projeto principal.
    infra/      # Subprojeto para a infraestrutura.
    site/       # Subprojeto para o site.
    specs/      # Subprojeto para as especificações.
    AGENTS.md   # Instruções para agentes de IA.
    LICENSE     # Licença do projeto.
    README.md   # README do projeto.

Com o repositório criado, segui para as especificações.

Especificações

Usei SDD para aumentar o alinhamento entre os humanos (eu) e a IA (agentes). O SDD, ou Spec Driven Development, é uma abordagem de desenvolvimento onde as especificações devem ser escritas antes do código. As especificações são arquivos Markdown em linguagem natural, que definem e descrevem o porquê, o quê e o como.

Criei 3 especificações, nessa ordem:

  1. specs/PROJECT.md: especificação do projeto (porquê).
  2. specs/DESIGN.md: especificação do design (quê).
  3. specs/TASKS.md: especificação das tarefas (como).

Comecei com a especificação do projeto, definindo um resumo do projeto, quais métricas de sucesso, funcionalidades (páginas) e testes (E2E). Por exemplo, defini que a página de artigos deveria apresentar uma lista de artigos ordenados por data decrescente, com título, data e resumo. Também defini que o teste E2E deveria acessar a página pela URL correta (/artigos) e validar se os artigos estavam visíveis e ordenados corretamente.

Depois segui para a especificação do design, definindo o que deveria ser feito para implementar o projeto definido na especificação anterior. Por exemplo, defini a stack de tecnologias, e que os artigos deveriam ser gerenciados usando arquivos Markdown e Frontmatter.

A stack de tecnologias que defini foi:

  • Javascript como linguagem principal.
  • Node como runtime de execução.
  • NPM como gerenciador de pacotes e automações.
  • Playwright como ferramentas de teste E2E.
  • Astro como framework para a construção do site.
  • Markdown como linguagem de marcação para conteúdo.
  • Frontmatter como gerenciador de metadados para conteúdo.
  • GitHub como repositório de código e automação de CI/CD.
  • Terraform como infraestrutura como código.
  • AWS como provedor de infraestrutura em nuvem.
  • Google Analytics como ferramenta de monitoramento.

Finalmente, segui para a especificação das tarefas, definindo as tarefas necessárias para implement o projeto com o design.

Usei o agente para criar e revisar todas as especificações.

Adicionei instruções no AGENTS.md para o agente considerar as especificações na geração de código.

Não usei ferramentas de SDD, como o Kiro, Spec Kit ou OpenSpec. Fiquei curioso para ver como seria usar SDD sem ferramenta e este modelo simples funcionou.

Em um artigo futuro vou compartilhar mais sobre como uso SDD.

Com as especificações criadas, segui para os testes.

Testes

Usei TDD para garantir que o projeto continue funcionando conforme ele seja alterado. O TDD, ou Test Driven Development, é uma abordagem de desenvolvimento onde testes são criados antes do código. Os testes são códigos que verificam automaticamente se o projeto está funcionando e identificam se algo quebrou.

Escolhi testes E2E e o Playwright para escrever e executar os testes. Testes E2E funcionam bem para sites simples, simulando o acesso através de um navegador “de verdade”. O Playwright permite escrever, executar e ver os relatórios dos testes com velocidade e clareza.

Usei a estrutura de arquivos e diretórios recomendada pelo Playwright:

site/                       # Subprojeto para o site.
    tests/                  # Testes.
        articles.spec.js    # Teste da página Artigos.
    playwright.config.ts    # Configuração do Playwright.

Adicionei instruções no AGENTS.md para o agente sempre executar os testes a cada ciclo de desenvolvimento, evitando deixar o projeto quebrado.

Em um artigo futuro vou compartilhar mais sobre como uso TDD.

Com os testes escritos, segui para a definição e configuração do framework.

Framework

Usei o Astro para criar o site, aproveitando as funcionalidades de rotas, componentes, coleções, Markdown e Frontmatter. Além disso, o modelo SSR (Server Side Rendering) gera sites estáticos que tornam a arquitetura de publicação simples e têm boa performance (quase nenhum processamento no servidor e no cliente).

Usei a estrutura de arquivos e diretórios recomendada pelo Astro:

site/                           # Subprojeto do site.
    src/                        # Código-fonte.
        assets/                 # Assets.
            images/             # Imagens.
        components/             # Componentes reutilizáveis.
            ArticleCard.astro   # Card de artigo.
        content/                # Conteúdo.
            articles/           # Artigos.
                ola-mundo.md    # Este artigo.
        layouts/                # Layouts.
        pages/                  # Páginas.
            artigos/            # Páginas de Artigos.
                index.astro     # Página Artigos.
                [slug].astro    # Página Artigo.
    astro.config.mjs            # Configuração do Astro.
    package.json                # Dependências e automações.
    jsconfig.json               # Configuração do Javascript.

Com o framework configurado e estrutura inicial do projeto pronta, segui para o desenvolvimento.

Desenvolvimento

Com SDD, TDD, Playwright e Astro, cada rodada de desenvolvimento era clara e consistente.

O fluxo foi basicamente:

  1. Ver qual a próxima tarefa em specs/TASKS.md. Por exemplo “Criar página Artigos.”
  2. Criar uma branch para a nova tarefa. Por exemplo pagina-artigos.
  3. Gerar/atualizar as especificações do projeto e design.
  4. Gerar o código de testes usando o agente e o Playwright.
  5. Executar os testes e falhar.
  6. Gerar o código para implementar a tarefa usando o agente e o Astro.
  7. Executar os testes e passar.
  8. Revisar e refatorar o código gerado.
  9. Executar os testes e passar.
  10. Criar o commit e fazer merge com a branch main.
  11. Atualizar a especificação de tarefas e ir para a próxima.

A parte mais importante é revisar e refatorar o código, principalmente quando você ainda não acertou a especificação e as instruções no AGENTS.md. É comum o agente ou o humano criarem código duplicado, difícil de entender e que quebram o projeto.

Caso eu ou o agente quebrássemos o código, os testes identificariam rápido. Além disso, o uso de branches permite voltar para o último estado estável rapidamente.

CI

TODO: Escrever sobre o processo de CI.

Infraestrutura

TODO: Escrever sobre o processo de infraestrutura.

CD

TODO: Escrever sobre o processo de CD.

Métricas

TODO: Escrever sobre o processo de métricas.

Conclusão

TODO: Escrever a conclusão. Incluir aprendizados (o que funcionou, o que não funcionou).