1 pontos por GN⁺ 2024-11-13 | 1 comentários | Compartilhar no WhatsApp
  • Motivado pela experiência de ver uma demissão remover o único contribuidor de um código que gerava receita, um desenvolvedor quis criar um plugin de truck factor para o GitHub Enterprise que encontrasse as “pessoas que não podem ser perdidas”
  • Os colegas temiam que essa métrica logo caísse na Lei de Goodhart, tornando-se uma ferramenta de gestão para encontrar “pessoas que podem ser demitidas”, em vez das que deveriam ser protegidas
  • O repositório e os dados originais do Truck-Factor ainda estavam disponíveis, mas a data de coleta dos dados era incerta e o procedimento do README não era reproduzível exatamente como estava, exigindo ajustes manuais
  • O recálculo consistiu em clonar vários repositórios do GitHub com gnu parallel e depois executar código Java; o Linux kernel teve truck factor 12 sem o filtro do linguist e 8 após aplicar o filtro
  • O resultado ficou abaixo dos números do artigo original — 90 no preprint de 2015 e 57 na publicação final —, o que torna difícil dizer que o bus factor do Linux kernel melhorou

Bus Factor e a ideia de um plugin perigoso

  • Bus Factor, ou Truck Factor, é o número mínimo de membros da equipe que precisariam desaparecer repentinamente antes que um projeto pare por falta de pessoas com conhecimento
  • Por volta de 2015, durante um processo de demissões na empresa, o ponto de partida foi o caso em que o único contribuidor de parte de uma base de código que gerava dinheiro para a empresa foi demitido
  • Depois de lembrar do Truck Number, surgiu a ideia de calcular, como um plugin para GitHub Enterprise, “quem não pode ser demitido”
  • Ao apresentar esse plugin por 5 minutos em uma lightning talk numa quinta-feira à tarde, os colegas viram que gestores poderiam usá-lo como ferramenta para encontrar “quem pode ser demitido”
  • O ponto central dessa reação era a Lei de Goodhart

A pesquisa existente sobre Truck Factor e a tentativa de reprodução

  • O estudo original calculava, em vários projetos populares do GitHub, quantas pessoas precisariam desaparecer para que o projeto parasse
  • Entre os alvos estava também o Linux kernel
  • No começo do texto, aparece que o primeiro preprint dizia que o Linux pararia se 80 pessoas saíssem; mais adiante, os números são resumidos como 90 no preprint de 2015 e 57 na publicação completa
  • Junto com mclare, foi feita uma tentativa de reproduzir os resultados para verificar se o truck factor havia melhorado cerca de 10 anos depois
  • O repositório no GitHub dos autores originais ainda estava disponível

Limitações dos dados e do ambiente de execução

  • Os dados do artigo são fornecidos em JSON, e a visualização original se baseava em um CSV que podia ser raspado
  • Porém, não era possível saber a data de coleta dos dados
  • As instruções do README não funcionavam como estavam, então foi preciso consultar issues do GitHub e corrigir o modo de execução
  • A lista de repositórios do GitHub foi extraída da primeira coluna do CSV original, e todos os repositórios foram clonados
  • Vários comandos git clone foram executados simultaneamente com gnu parallel

gnu parallel, linguist e os bloqueios no NixOS

  • Mesmo especificando -j 8 no gnu parallel, todos os 32 cores do notebook acabaram sendo usados
  • Havia 8 processos git clone visíveis ao mesmo tempo, enquanto vários processos git index-pack usavam todos os cores
  • Uma possível causa levantada foi que git index-pack fosse um subprocesso criado por fork, levando o parallel a iniciar outros git clone
  • O código do Truck Factor usa o linguist do GitHub para excluir arquivos de documentação
  • No ambiente NixOS, sem experiência com Ruby, não foi possível resolver a instalação de Ruby Gems a tempo; foi pedido um método para instalar o plugin linguist em um Nix flake ou um pull request

Procedimento real de recálculo

  • O repositório original foi bifurcado e clonado localmente, e o modo de execução foi ajustado seguindo o README
  • O código-fonte Java foi compilado em um jar com mvn package
  • Primeiro, cada etapa foi testada com o repositório do GitHub do numpy; depois, foi feito o recálculo de todos os repositórios
  • mclare baixou o CSV da visualização original e converteu a primeira coluna em uma lista de repositórios do GitHub
  • O fluxo de execução foi o seguinte
    • Clonar os repositórios com parallel -j 8 git clone ::: $(cat ../meta/repo_list.txt)
    • Entrar no diretório gittruckfactor/scripts para evitar um erro do awk
    • Extrair as informações de commits git de cada repositório com commit_log_script.sh
    • Executar gittruckfactor-1.0.jar para processar os dados de commit extraídos
  • Em uma conexão doméstica rápida de internet gigabit, clonar todos os repositórios sequencialmente levou 17,5 minutos
  • O processamento de cada repositório também parece ter levado cerca de 18 minutos

Resultado do recálculo para o Linux kernel

  • A saída de exemplo do Linux kernel foi TF = 12, coverage = 49,98%
  • Entre os TF authors estavam Linus Torvalds, Mauro Carvalho Chehab, Rob Herring, Thomas Gleixner, Krzysztof Kozlowski e outros
  • Linus Torvalds aparecia com 5.712 arquivos, 6,59%
  • Sem o plugin linguist, que filtraria documentação e bibliotecas de terceiros, o resultado foi truck factor 12 para o Linux kernel
  • Depois que mclare instalou o plugin linguist em seu próprio sistema, o truck factor obtido para o Linux kernel foi 8

Elementos ausentes no cálculo e próximos pontos a verificar

  • Esse cálculo não reflete o processo de revisão
  • Há o problema de que, conforme a senioridade aumenta, desenvolvedores precisam revisar mais, em vez de escrever código diretamente no teclado
  • Outros itens a verificar são os seguintes
    • se o cálculo de truck factor leva em conta co-authored-by do git e cabeçalhos de reviewer
    • se não levar, se é possível incluí-los no cálculo
    • por que o número do Linux mudou tanto 10 anos depois
    • se o fato de não ter aplicado Levenshtein distance 1 para mesclar aliases de desenvolvedores, como no artigo original, afetou o resultado
    • se, ao fazer checkout do repositório do Linux kernel para meados de 2015, o mesmo código ainda produz 80
    • como o algoritmo foi atualizado em 2016, se é possível recalcular os números posteriores
  • É possível examinar as 156 citações do artigo original para verificar se há métodos melhores de cálculo
  • Projetos grandes mais recentes, como Rust, não foram incluídos no artigo de 2015, então é possível comparar projetos populares atuais com o histórico passado
  • Também seria possível criar um script que encontre o truck number por ano para um repositório git arbitrário

Bus Factor ainda menor

  • A pergunta que se queria verificar era se o truck factor havia melhorado com o tempo
  • O resultado fica mais próximo de não melhorou; piorou
  • Para o Linux kernel, o resultado desta execução ficou muito abaixo dos números do artigo original
  • Dependendo de filtrar ou não documentação e bibliotecas de terceiros, o resultado do Linux kernel cai ainda mais, de 12 para 8
  • Mais visualizações e detalhes podem ser encontrados no texto de mclare

1 comentários

 
GN⁺ 2024-11-13
Opiniões no Hacker News
  • Uma das funcionalidades de https://codescene.com/ é justamente isso
    Ela encontra ilhas de conhecimento e as correlaciona com código alterado com frequência, identificando hotspots perigosos: áreas com muitas mudanças, mas baixa distribuição de conhecimento
    Quando alguém anuncia que vai sair, fica fácil ver o código que só essa pessoa conhece, o que também facilita montar um plano de transição
    Nunca pensei que pudesse ser usado de forma abusiva; originalmente é uma ferramenta de visibilidade. Um gerente que a usa desse jeito é um péssimo gerente, e, se já é esse tipo de pessoa, essa ferramenta não vai mudar isso

    • Não dá para enxergar “abuso” de forma ingênua demais. Digamos que você faça parte do serviço de inteligência de um país. Suponha que o país Tussia, que tem o acesso bloqueado ao importante kernel Kinux usado em equipamentos militares no mundo todo, descubra que a pessoa do escritório ao lado começou um projeto para fazer um fork desse kernel para uso interno do próprio país
      Se você tiver ambição de ser promovido, poderia pedir ao departamento responsável por recrutamento “8 agentes mulheres com treinamento especial para criar intimidade com nerds” e, como plano de contingência em caso de falha, também pedir 8 doses de polônio
      Pode soar como pura ficção, mas conheço o caso de um CEO de uma startup unicórnio que estava buscando investimento seed e passou de fato por algo correspondente à primeira parte
    • Passei por três empresas em que o Pluralsight Flow foi adotado; em duas delas, os gestores imediatamente começaram a usar as métricas para feedback, avaliações de desempenho e decisões de contratação/demissão
      Na terceira, os desenvolvedores reconheceram esse padrão de longe e se recusaram a usar a ferramenta ou a aceitar a própria avaliação
      Ferramentas desse tipo são absurdamente caras, então quem aprovou precisa extrair ROI de algum jeito. Como não há uma boa forma de medir produtividade, entregas ou silos de conhecimento, acaba descambando para coisas como “Jose abriu poucos PRs esta semana”
    • O uso para visibilidade em si é excelente, mas só quando consegue permanecer dentro desse escopo
      O problema é que os próprios desenvolvedores podem ver isso e tentar migrar para projetos ou componentes-alvo para entrar na lista de funcionários impossíveis de demitir. Idealmente, os trabalhadores poderiam se mover em conjunto e reduzir o truck factor a 0, tornando difícil demitir qualquer pessoa
      É claro que, nesse ponto, vira quase uma perda total de tempo e comprova o ponto original dos colegas do blogueiro: “isso vai cair imediatamente na Goodhart’s Law”
    • Uma consultoria externa também poderia usar isso para ajudar a empresa com demissões em massa. Isso pode acontecer por melhor que seja o gerente
  • Na Amazon, é fácil ver números assim nos sistemas de código, como relatórios que qualquer gerente pode executar, e também há várias outras formas de entender o que a equipe faz e quais riscos existem. Pessoalmente, acho útil
    O bus factor é apenas uma perspectiva; por outra perspectiva, ele permite encontrar e corrigir silos, engenheiros que não colaboram com outras pessoas e áreas em que é difícil realocar engenheiros
    Alguns desenvolvedores têm medo de serem substituíveis e acham que um sistema que só eles conhecem é segurança no emprego, mas, por outro lado, isso é um risco técnico e pode impedir um bom engenheiro de ir para projetos mais importantes. Também pode ser um caminho para fazer outra coisa quando você se cansa de um sistema de que não gosta

    • Não tenho medo de ser substituível. Se um lugar não me quer, eu também não quero estar lá
      Mas a ideia de substituibilidade cria um grande overhead e impede que pessoas talentosas sejam usadas em sua capacidade máxima, porque elas, na prática, não são substituíveis
      Em alguns lugares isso é necessário, mas em outros o overhead de processo se torna um risco muito maior para o sucesso do projeto do que o bus factor
    • Conheço um desenvolvedor que teve transferência e promoção negadas porque não havia como substituí-lo facilmente
      O resultado foi que ele saiu da empresa em até 3 meses
    • “Se você não pode ser substituído, não pode ser promovido”
    • Do ponto de vista de um funcionário cujo objetivo principal não é otimizar o lucro da empresa, achar que um sistema que só ele conhece dá segurança no emprego também é uma estratégia realista
    • Ao longo de toda a minha carreira, tentei tornar a mim e outros desenvolvedores o mais substituíveis possível. Parte considerável do trabalho de digitalização é justamente isso, e também porque lidar com silos de conhecimento é irritante
      Um dos motivos para eu usar bastante TypeScript também no backend é que isso reduz para uma só a quantidade de linguagens que uma equipe pequena precisa conhecer. Assim, quando um desenvolvedor frontend sai de férias, ele pode realmente se desconectar, e outra pessoa consegue cobrir. Se alguém muda de emprego, dói menos
      Nunca tive problemas com isso e vejo a substituibilidade como parte de um sistema saudável. Depois de alguns anos na gestão, uma das primeiras coisas que aprendi foi que “todo mundo é substituível; é só uma questão de custo”. Portanto, se o nível de conhecimento de alguém for alto demais, isso pode até jogar contra a pessoa, porque a liderança vai tentar reduzir esse risco. Especialmente porque demissões em massa por razões econômicas costumam ser bastante aleatórias
      Dito isso, eu não gostaria de trabalhar em um lugar que usa métricas ridículas assim. Quanto mais burocracia se coloca no caminho de fazer um bom trabalho, menor a chance de eu querer trabalhar junto. Coisas desse tipo tendem a fazer as pessoas jogarem com as métricas em vez de fazerem um bom trabalho, criando uma cultura ruim para produtividade e qualidade
  • O gnu parallel está executando 8 operações de git clone ao mesmo tempo, como foi solicitado, e cada git clone está iniciando por conta própria vários threads de index-pack
    Aqui, ajuda definir temporariamente pack.threads como 1 com git config

    • É um problema cada vez mais comum. As duas camadas paralelizam pelo número de CPUs ou núcleos e tentam usar a máquina inteira, e na camada interna acabam surgindo N² threads/processos
      Como cresce ao quadrado, quanto mais CPUs houver, pior fica o problema. Com 32 núcleos, 32² = 1024; na prática, como foram especificados 8 no Parallel, provavelmente teria parado em algo como no máximo 256 processos index-pack. Ainda assim, é preciso muita memória para aguentar isso e, na prática, não há benefício nenhum
      A solução é paralelizar apenas uma das duas camadas
      Sobre pack.threads, a explicação em man git-config é esta: especifica o número de threads a criar ao procurar as melhores correspondências de delta, e git-pack-objects(1) precisa ter sido compilado com pthreads. Caso contrário, é ignorado com um aviso. É uma opção para reduzir o tempo de empacotamento em máquinas multiprocessadas, mas a memória necessária para a janela de busca de deltas é multiplicada pelo número de threads. Ao especificar 0, o Git detecta automaticamente o número de CPUs e define o número de threads de acordo
    • Em vez de fazer uma configuração temporária com git config, basta usar git -c pack.threads=1 clone: https://git-scm.com/docs/git#Documentation/git.txt--cltnameg...
  • Essa interpretação não é muito boa. Vejo este texto como algo para todos os líderes de engenharia
    O bus factor significa o quanto a equipe sofreria se alguém da equipe, ou você mesmo, fosse atropelado por um ônibus
    O bus factor ideal para todos os membros da equipe é 0. À primeira vista pode soar como “tornar todos descartáveis”, mas na verdade é quase o oposto, e esse é o ponto
    A equipe deve ser boa o suficiente para ser a) autônoma e b) livre de mistérios. No estado ideal, todos entendem como tudo funciona. Um novo funcionário deve conseguir começar a gerar valor imediatamente, e quem sai deve poder ficar tranquilo sabendo que não ficou nenhuma área desconhecida para trás
    Uma equipe ideal em que todos têm BF 0 é desejável. Isso significa que os membros da equipe são substituíveis e que, se alguém ficar doente, sair de férias, sair de fato ou for removido, qualquer membro da equipe consegue preencher a lacuna
    Mais importante ainda, BF 0 é um reflexo de simplicidade. O software, os pipelines de build, teste e deploy, a documentação e a estrutura de suporte devem ser coesos e consistentes. Siloizar informações dentro de membros da equipe é ruim, e todos devem conseguir fazer build e deploy
    BF 0 é um indicador saudável, mas nunca é medido por número de e-mails, número de commits, número de PRs, linhas de código, velocidade de resposta ou heatmaps do GitHub. Essas métricas não mostram nada e, pior, são métricas nocivas e terríveis
    Avaliar pessoas por essas métricas não é diferente de macacos diante de uma máquina de escrever. Mais startups precisam ouvir isso

    • Sempre ouvi bus factor no sentido oposto. Algo como “quantas pessoas precisam ser atropeladas por um ônibus para que o projeto não possa continuar”, e eu entendia que o valor ideal era igual ao número de membros da equipe
      Parece que estamos falando do mesmo conceito, mas é surpreendente que esse número nem sempre seja usado na mesma direção
    • Já trabalhei em um projeto em que havia apenas um punhado de pessoas no mundo com determinada habilidade técnica. Naquele momento, o bus factor era claramente 1
      Em projetos que empurram os limites do que é possível, simplicidade às vezes não é uma opção. Claro que isso é uma pequena fração de todos os projetos de software, mas, quando se faz algo inédito, a preocupação maior é “como diabos vamos conseguir fazer isso”, mais do que manter o código o mais simples possível
      Não quer dizer que a qualidade do código possa ser baixa. Mas, ao fazer coisas difíceis, às vezes é preciso código complexo, e só algumas gerações depois os padrões de design se consolidam a ponto de permitir transformar aquela coisa difícil em código menos complexo. Isso pode levar 10 anos
    • Se, desde o primeiro dia, qualquer pessoa consegue entender o código e nada exige conhecimento de domínio, qual é a proposta de valor desse produto ou dessa equipe?
      Se a coisa mais complexa que conseguem construir é algo como um app de tarefas, acho que não geram muito valor para a sociedade
    • Quem faz bem o próprio trabalho e tem confiança tenta ativamente reduzir o próprio bus factor
      Um bus factor alto significa que o empregador está segurando você pelo que você fez no passado, não pelo seu potencial futuro
    • O exército pensa assim. Parte do princípio de que precisa continuar funcionando mesmo perdendo pessoas
  • O argumento central do artigo original é este trecho
    “Nossa estimativa depende da suposição de cobertura. Se o conjunto atual de autores cobrir menos de 50% do conjunto atual de arquivos do sistema, é provável que o sistema sofra atrasos graves ou pare”
    Aqui, o autor de um arquivo é definido como um usuário que fez uma contribuição significativa para aquele arquivo segundo um peso pré-calculado

  • Por um lado, eu ficaria até surpreso se esse tipo de métrica de dashboard já não estivesse incluído em algum software corporativo. A diretoria da minha empresa anterior chegou a perguntar de verdade se dava para criar um relatório diário dizendo quem no departamento mais enviava e recebia e-mails
    Recusei porque não gostei de para onde aquilo poderia ir, mas outro colega acabou criando. Como esperado, a pessoa que mais recebia e enviava e-mails era o administrador de sistemas, porque a conta dele estava configurada como remetente automático de e-mails de vários servidores. Ele enviava centenas de e-mails de alerta por dia para si mesmo, além de newsletters e e-mails de resumo que assinava
    Por outro lado, se todos os colegas pediram para você não fazer algo que pode afetar os empregos deles e mesmo assim você insiste como projeto de hobby, isso soa como uma atitude bem maldosa

    • Em 2015, quando meus colegas disseram para eu não fazer, eu não fiz
      Só quero ver se o software open source que uso distribuiu conhecimento bem o suficiente para aumentar suas chances de sobrevivência
      Eu recusei aquela atitude maldosa
    • É uma métrica absurda
  • Acho que “quanto mais o desenvolvedor sobe na escada da carreira, menos deve colocar a mão no teclado e mais deve fazer reviews” é um equívoco comum em empresas de tecnologia
    Não queremos transformar um ótimo desenvolvedor em um gerente medíocre

    • Exato. Há tech leads com excelente capacidade de escrever código, mas péssimos em competências como liderança ou feedback
      Ele ficaria muito melhor como desenvolvedor sênior do que como tech lead. É difícil imaginar o quanto a equipe sofreria se ele virasse gerente
    • Se você considera code review como “gestão”, isso é bastante preocupante
  • A triste ironia disso é que a pergunta ainda está errada
    Quando uma startup precisa fazer demissões, a pergunta não é “quem podemos demitir e ainda manter o negócio atual?”, mas sim “qual é a equipe que vai construir a próxima versão do produto rápido o suficiente para a empresa não quebrar?”
    Toda encruzilhada, no fim, é uma encruzilhada, e muitas empresas morreram por não escolherem um caminho rápido o bastante

  • O CPAN já acompanha há muito tempo o fator ônibus. Por exemplo, https://metacpan.org/pod/Moose mostra Bus Factor 5 na coluna de informações à esquerda

  • Gostamos de chamar isso de fator loteria
    A ideia é: o projeto conseguiria continuar se alguém ganhasse na loteria e fosse para uma ilha tropical sem rede elétrica nem telecomunicações?
    Assim soa menos macabro

    • Quem ganha na loteria dá aviso prévio de 2 semanas e, se for realmente necessário, ainda dá para ligar depois
      Quem é atropelado por um ônibus desaparece imediatamente. Não é a mesma coisa
    • Um bom funcionário vai querer repassar seu projeto e responder perguntas, mas também é preciso se preparar para casos em que isso não seja possível
    • Usar “morte súbita” como eufemismo para mudança de emprego deixa um gosto ruim
      Há quem não goste de metáforas esportivas, mas acho que pelo menos são melhores do que metáforas militares
      De qualquer forma, muitas vezes também não há transição, então talvez o elemento de surpresa em si nem seja tão importante
    • Ser atropelado por um ônibus pode ser a opção mais fácil, então essa possibilidade também deve ser levada em conta
    • Não conheço ninguém que tenha ganhado uma grande loteria ou sido atropelado por um ônibus, mas conheço várias pessoas que pediram demissão depois de ficarem ricas com criptomoedas