3 pontos por GN⁺ 2025-06-23 | 1 comentários | Compartilhar no WhatsApp
  • Git notes é um recurso que anexa metadados a um namespace separado sem alterar objetos do Git, mas não é amplamente usado por causa da baixa usabilidade e da adoção limitada
  • Permite acrescentar novas informações sem precisar corrigir mensagens de commit antigas, o que combina bem com registros deixados por sistemas automatizados, como informações de review, build e tickets
  • O projeto Git e o Gerrit usam notes na prática para permitir ver no git log discussões da lista de e-mails, resultados de testes e informações de revisores por commit
  • O git-appraise do Google implementa code review distribuído sobre git notes, permitindo fazer solicitação de review, comentários, reviews e merge localmente
  • O GitHub parou de exibir commit notes em 2014, e notes de blob e tree exigem familiaridade com comandos internos do Git, o que dificulta o uso apesar do potencial de distribuir o histórico do projeto

Metadados sem alterar objetos do Git

  • Git notes é um recurso para armazenar metadados separados em objetos rastreados pelo Git
    • O alvo inclui não só commits, mas também blob e tree
    • As informações são anexadas em um namespace separado, sem modificar o próprio objeto
  • Mensagens de commit que já entraram no histórico normalmente não podem ser corrigidas com segurança com facilidade, mas com notes é possível adicionar novas informações até mesmo a commits antigos
    • É possível anexar uma nota com git notes add -m, assim
      git notes add -m 'Acked-by: <tyler@tylercipriani.com>'
      
    • Depois, ela aparece no git log como um bloco Notes: abaixo do commit correspondente
  • Em 2010, Scott Chacon escreveu no GitHub.blog que notes é mais adequado para anexar registros automatizados, como os de sistemas de tickets e build, do que conversas com outros desenvolvedores

Uso real e onde trava

  • O projeto Git usa notes para conectar cada commit a discussões na lista de e-mails
  • Notes também pode ser usado para rastrear tempo de trabalho por commit ou branch, adicionar informações de review e teste ao git log e até fazer code review totalmente distribuído
  • O plugin reviewnotes do Gerrit permite ver metadados de code review dentro do Git, até offline
    • Os comandos para buscar e exibir notes são os seguintes
      git fetch origin refs/notes/review:refs/notes/review
      git log --show-notes=review
      
    • As informações exibidas incluem Verified+1, Verified+2, Code-Review+2, Submitted-by, Submitted-at, Reviewed-on, Project, Branch e outros
  • O git-appraise do Google é um sistema de “fully distributed code review” construído sobre git notes
    • Funciona de forma independente de code forges como GitHub e GitLab
    • Permite solicitar review de mudanças, comentar mudanças, fazer review e merge no computador local
    • Também inclui uma interface web
  • O maior ponto fraco é a usabilidade
    • O GitHub parou de exibir commit notes em 2014
    • Para commit notes, dá para facilitar parcialmente o fetch automático e a exibição no git log com configuração no gitconfig
      git config --add \
      remote.origin.fetch \
      '+refs/notes/*:refs/notes/*'
      
      git config \
      notes.displayRef \
      'refs/notes/*'
      
    • Para armazenar notes em blob ou tree, é preciso estar familiarizado com o plumbing do Git
  • O Git distribui o histórico do código, mas grande parte do valor de um repositório Git fica presa dentro de forges como o GitHub
    • Git notes pode ser um caminho para distribuir não só o código, mas também todo o histórico do projeto

1 comentários

 
GN⁺ 2025-06-23
Opiniões no Hacker News
  • Outro recurso pouco conhecido é o git trailers: https://alchemists.io/articles/git_trailers
    São dados estruturados em chave-valor que podem ser incluídos ao criar commits, e alguns sistemas os usam para anexar metadados. Por exemplo, o Gerrit usa esse recurso para adicionar o Change-Id

    • Um recurso parecido em outro sistema é o PostgreSQL COMMENT: https://www.postgresql.org/docs/17/sql-comment.html
      Ele permite anexar texto a vários objetos de banco de dados do PostgreSQL. Seria bom se o PostgreSQL também tivesse um recurso de metadados editáveis de objetos de banco de dados em formato estruturado de chave-valor
    • Descobri recentemente que o GitHub usa git trailers como alternativa a colocar [skip ci], provavelmente para facilitar a remoção por subsistemas que consomem mensagens de commit: https://docs.github.com/en/actions/managing-workflow-runs-an...
      Não sei por que eles impõem que seja o último trailer; talvez por causa de regex
    • Usei git notes para marcar, entre os commits do meu branch, aqueles em que eu havia rodado testes unitários, e fazia um script pular esses commits
      Era útil quando eu trabalhava com um upstream open source e queria deixar meu branch perfeitamente polido com git rebase -i. Hoje, parece melhor colocar essa informação em git trailers. Sobre o Change-Id, seria bom se o próprio Git tivesse esse tipo de identificador, para que as ferramentas também pudessem entendê-lo. Identificar commits pela mensagem de commit é frágil, especialmente em MRs em que a mensagem pode ser alterada. O ID do commit identifica um commit de forma única, mas não é um identificador útil quando a mesma alteração pode ser movida para cima de outro commit. Dito isso, trailers fazem parte do commit real, enquanto notes não fazem, então não seriam um bom substituto para o meu caso de uso
    • Interessante, eu não conhecia esse recurso. Gosto de conventional commits, e trailers parecem uma forma melhor de adicionar esse tipo de metadado
      Fico me perguntando se colocar manualmente na mensagem de commit e usar a flag --trailer são funcionalmente equivalentes
    • Sinto muita falta do Gerrit que eu usava quando trabalhava na GOOG, mas, para os padrões dos anos 2020, a história de implantação é bem ruim
      Tentei subir uma instância local e integrá-la a um repositório hospedado no GitHub, mas só encontrei frustração. Fico me perguntando se existe alguma alternativa que lide melhor que o GitHub com rastreamento de alterações entre commits etc., mas que seja desenvolvida de forma mais ativa e tenha integração mais amigável com o GitHub. Eu realmente odeio as ferramentas de code review do GitHub
  • O Forgejo também dá suporte a isso desde a versão 10, lançada em janeiro deste ano: https://forgejo.org/2025-01-release-v10-0/#new-features
    https://codeberg.org/forgejo/forgejo/pulls/4753

  • Parece realmente muito legal, mas fico curioso sobre como notes funcionam junto com recursos de reescrita de histórico que, na prática, substituem commits por cópias modificadas, como amend ou rebase
    Pelo que parece, notes são anexadas a um commit, tree ou blob ID específico. Fico me perguntando se git rebase e similares são inteligentes o suficiente para copiar notes para os novos commits, ou se elas simplesmente desaparecem. Também me pergunto o que acontece quando vários commits são combinados em um só com squash em um rebase interativo. Anexar notes a blobs e trees parece ter o mesmo problema. Dá a sensação de anexar metadados a um arquivo ou diretório no repositório, mas, na verdade, eles ficam anexados a um conteúdo específico. Por exemplo, se eu anexar uma note a um blob que contém a string "Hello world!", o Git associaria essa note a todos os arquivos com esse conteúdo? E, se eu alterar um arquivo para "Hello, world!", perderia as notes?

    • Isso é configurável. Por padrão, operações de amend e rebase copiam notes adiante. Veja o item notes.rewrite em git-config(1)
  • Uso Git há talvez uns 10 anos e não sabia que existia git notes. Legal
    O pedido para que “todos os forges disponibilizem metadados de code review dentro do Git para uso offline” provavelmente não vai colar muito com forges comerciais como o GitHub. Como você mesmo disse, muito do valor de um repositório Git fica trancado em forges como o GitHub. Empresas com fins lucrativos normalmente não têm muito incentivo para tornar genérico aquilo que elas agregam como valor. Não estou querendo criticar o GitHub; acho que eles fazem um bom trabalho ao oferecer um ótimo serviço e um tier gratuito muito generoso, além de permitir extrair todos os dados via API se você quiser sair. É simplesmente a natureza da operação comercial

    • Primeiro seria preciso lançar um novo serviço que use esse recurso como diferencial; aí os concorrentes talvez o adicionem também para tentar acompanhar
  • Git notes só são legais quando você adiciona texto com frequência depois que o commit já foi criado e visto por outras pessoas
    Os exemplos de Acked-By e links para discussões em listas de e-mail não parecem bons exemplos. É bem provável que ambos já sejam conhecidos no momento de criar o commit. Mensagens de commit do Git praticamente não têm limite de tamanho, então também seria possível copiar para a própria mensagem do commit a discussão relacionada ao commit que aconteceu no forge. Um exemplo melhor, a meu ver, seria adicionar uma git note a um commit que foi revertido posteriormente

    • Um modo de falha comum é a mensagem de commit declarar com confiança que corrigiu um bug que, na verdade, não corrigiu. E ainda vincular a um único bug os bugs em cadeia criados pela correção
      Talvez eu seja estranho, mas já vi colegas demais que não olham direito comentários ou annotate para lembrar por que o código foi escrito daquele jeito em primeiro lugar. Eles simplesmente saem mudando e torcem para que o problema não seja associado a eles. Mas, depois de lidar com clientes irritados que só estavam esperando a correção de um bug e, pouco tempo depois, ver esse bug voltar, você tende a ficar mais cuidadoso com correções. Para corrigir vários bugs de uma vez, muitas vezes é preciso refatorar, e a refatoração também pode abrir oportunidades para novos recursos ou melhorias de desempenho
    • Discussões sobre um commit, isto é, revisão e aprovação do commit (Ack), não podem acontecer antes de o commit ser criado
      Para deixar uma marca em um commit que foi revertido depois, a mensagem de commit é melhor. Ao fazer blame em um arquivo, você vê a alteração mais recente daquele arquivo; se um commit reverteu a alteração de outro commit, o commit de reversão mais recente aparece no blame
    • A discussão pode continuar mesmo depois que o commit é criado
  • Isso não é falta de conhecimento, é um problema de UI. Se a UI do GitHub mostrasse notes, o uso aumentaria muito imediatamente

    • Eu gostaria que o GitHub desse suporte a isso
  • Há muitos “recursos mais legais, mas menos amados do Git”. Por exemplo, bisect, pickaxe, reflog, range-diff, archive, annotated tags etc.
    É uma pena que esses recursos sejam frequentemente esquecidos porque muita gente pensa no Git apenas como uma espécie de Google Drive sofisticado

    • Git notes, de todo modo, são redundantes para rastreamento de funcionalidades, pois isso exige uma ferramenta de gerenciamento de projetos de nível mais alto. É preciso ter roadmap, hierarquia de funcionalidades, detalhes não técnicos; pense em um rastreador grande ou no Jira
      Ainda assim, acho isso ok. A filosofia Unix é focar em uma coisa e fazê-la bem
    • Em muitos casos, é porque esses recursos na prática não são tão úteis assim e ficam mais perto de enfeites ao redor das ferramentas centrais que fazem o trabalho pesado
    • Eu esperava conhecer todos os recursos listados, mas fui pego de surpresa pelo pickaxe. Não devo ficar confiante demais
  • O projeto LibreOffice usou Git notes para rastrear cada commit do repositório do Apache OpenOffice
    Ao espelhar esse repositório como uma branch do repositório Git do LibreOffice, eles registravam se cada commit era uma alteração irrelevante, por exemplo uma mudança no sistema de build que o LibreOffice já havia substituído por algo melhor havia muito tempo; se era duplicada de uma alteração que já existia no LibreOffice; ou, em casos raros, se havia sido aceita no LibreOffice e por qual commit havia sido cherry-picked. Ainda dá para ver isso diretamente em https://cgit.freedesktop.org/libreoffice/core/log/?h=aoo/tru..., e esse front-end Git ainda exibe notes. Há alguns anos eles pararam de rastrear essas alterações, provavelmente porque o ritmo de mudanças do Apache OpenOffice ficou muito lento e já não havia muito ganho em fazer cherry-pick das poucas alterações existentes

  • Não é o recurso mais legal, mas menos amado; está mais para um recurso-gimmick que poderia ter sido legal em casos muito específicos, como uma equipe em que a empresa inteira é tocada só por desenvolvedores
    O que é necessário entra na mensagem de commit, e referenciar um ticket de um sistema separado não é bug, é feature. Isso porque JIRA ou outros sistemas são usados para comunicação com não desenvolvedores. Por exemplo, analistas de negócio não têm nenhum acesso ao código ou ao repositório, e o pessoal de suporte também não tem acesso ao repositório nem ao código. Seria possível criar um front-end para que não desenvolvedores vissem e editassem notes, mas ainda assim isso não faria muito sentido. BAs, suporte e afins não se interessam por commits específicos; uma funcionalidade pode coincidir exatamente com um único commit, mas normalmente não é assim. Quando se usam vários repositórios e uma funcionalidade atravessa vários serviços, git notes ficam bem inúteis, e no fim é preciso uma referência a um sistema externo

    • Acho até estranho que analistas de negócio ou pessoas de suporte não recebam acesso ao código e ao repositório. Qual é a vantagem de tratar o próprio produto como uma caixa-preta?
      Mas isso é o padrão dominante. Às vezes, um analista de outra equipe que compartilha o mesmo monorepo me faz uma pergunta que poderia ser respondida diretamente com uma linha de código. E esse analista é até técnico e sabe SQL; nosso código também é escrito de forma muito idiomática e em alto nível. Ainda assim, a cultura não consegue mudar sozinha até morrer por causa de sua ineficiência intrínseca
    • Há muitos dados externos ao commit que não pertencem à mensagem de commit, mas são relevantes. Status de aprovação dos testes[1], registros de testes manuais, iterações de code review, anotações deixadas ao investigar um commit problemático com mais de 6 meses, e coisas do tipo
      [^1] https://news.ycombinator.com/item?id=44348438
  • Uma solicitação de recurso de 9 anos pedindo suporte a notes no GitLab foi fechada recentemente: https://gitlab.com/gitlab-org/gitlab/-/issues/15029
    Infelizmente é preciso fazer login para ler, mas qualquer conta do gitlab.com deve servir

    • Há também outra issue com uma proposta mais completa: https://gitlab.com/gitlab-org/gitlab/-/issues/216351
    • Para quem estiver curioso: ela não foi fechada por ter sido concluída, mas por abandono: “Como este não é um foco atual nessa área, estamos fechando esta solicitação de recurso”