Árvore genealógica dentro de git

Feliz dia do programador! Desejo a você compromissos mais brilhantes, solicitações de recebimento mescladas, menos conflitos de mesclagem e que seus ramos de vida permaneçam relevantes pelo maior tempo possível. Como presente conceitual, proponho a implementação de uma árvore genealógica por meio do sistema de controle de versão Git. Bem ... parece um plano!



Para aqueles que entenderam tudo imediatamente, dou links para o código fonte: GenealogyTreeInGit e árvores genealógicas: meus e presidentes dos EUA .


Além disso, implementei um gráfico social simples. Ele exibe não apenas o grau de parentesco, mas também o status das relações entre os descendentes, eventos como casamento, divórcio, parto e também contribuições para as relações.


Git


Deixe-me lembrá-lo de que o Git é um dos sistemas de controle de versão mais populares. É poderoso: você pode confirmar alterações, criar (checkout) e mesclar ramificações, comparar diferentes versões de arquivos (diff), identificar autores de strings específicas (culpar) e fazer muitas outras coisas.

Felizmente ou infelizmente, o Git é semelhante ao vencedor que reescreve a história: permite alterar datas, mensagens e autores de confirmações. Mas isso permite adicionar membros da família, como se fossem os autores de eventos feitos em uma data específica.


Comecei pequeno: escrevi vários comandos e pronto, um fragmento da árvore está pronto. Fine Agora vamos fazer isso com todo o exército de parentes. Ficarei feliz em escrever 200 linhas de código confuso para eles e 10 mil linhas para presidentes!


Você já me adicionou à lista de idiotas? Strike off. Obviamente, automatizei o processo e escrevi um aplicativo para converter dados genealógicos em uma sequência de comandos Git. Existem vários formatos para esses dados, eu escolhi o GEDCOM .


Gedcom


GEDCOM é uma especificação para troca de dados genealógicos. Este formato é bastante antigo, mas simples. A especificação está bem descrita na Internet. É apoiado por quase todos os programas genealógicos, por isso há muitos exemplos : presidentes dos EUA, dinastia real, Shakespeare.

Eu implementei toda essa bagunça no .NET Core - é conveniente e multiplataforma. Para analisar e processar o GEDCOM, existem várias bibliotecas C #, por exemplo, GeneGenie.Gedcom , gedcomx-csharp . Eu decidi escrever minha própria biblioteca baseada no GedcomParser , porque ela tem uma falha fatal ... Na verdade, não: eu só queria entender o formato e me livrar de todas as dependências, que permitiriam, se necessário, portar facilmente o projeto para outros idiomas


Geração de comando


É hora de processar os dados extraídos em um formato conveniente e gerar comandos Git para eles. Decidi classificar todos os eventos em ordem cronológica e, em seguida, criar ramificações, mesclar e enviá-los em ordem crescente de datas. Infelizmente, nem todos os eventos têm datas, portanto, não foi fácil classificar todos os eventos corretamente. Está chegando 2 ^ 2 ^ 3 dias, e percebi que essa abordagem não estava totalmente correta, pois a pesquisa em profundidade seria muito mais fácil. Talvez eu o corrija mais tarde.


Inicialização


Nesta fase, apenas inicializamos o repositório:


mkdir Family cd Family git init 

Eventos


Nesta parte do script, processamos e confirmamos todos os eventos. Para isso, foram utilizados os seguintes comandos:


  • git checkout --orphan branch_name
  • git merge @I1@ --allow-unrelated-histories --no-commit
  • git commit -m "msg" --date "" --author "name <email>" --allow-empty

O primeiro comando, checkout , cria uma ramificação para cada pessoa. O sinalizador --orphan permite criar ramificações órfãs, ou seja, ramificações sem pais. A ramificação órfã é criada uma vez - na próxima vez que você alternar ramificações usando o comando checkout esse parâmetro será omitido. No final, quase todos os commits têm pais, exceto os ancestrais mais distantes, pois os anteriores são desconhecidos.


O segundo comando, merge , une os pais e cria o filho. Escrevemos "Birth" com o ano correspondente na mensagem de confirmação. Também especificamos os sinalizadores --allow-unrelated-histories e --no-commit para permitir a mesclagem de ramificações órfãs e confirmar as alterações posteriormente. Algumas crianças são adotadas, por isso escrevemos "adotadas" para elas. Engraçado, mas o Git permite casamentos em grupo, ou seja, é possível mesclar mais de dois ramos por vez. E os ramos não têm sexo, então você pode chamá-los de "pai 1" e "pai 2". A propósito, também é possível criar pais solteiros.


Finalmente, o terceiro comando, commit , cria um novo commit com a mensagem -m , a data --date e o autor --author . Como já mencionei, o Git permite alterar a mensagem, o autor e a data do commit. Além disso, o Git permite que você crie confirmações sem arquivos com a bandeira - --allow-empty e sem mensagens com a bandeira - --allow-empty-message . O autor também precisa especificar um email, mas o Git aceita um email vazio - você só precisa escrever <> . Infelizmente, o Git não respeita os idosos: o limite inferior da data do commit é 1º de janeiro de 1970 (o "início" do Horário do Unix) - a data anterior será exibida incorretamente. No entanto, você pode simplesmente mencionar a data real na descrição. No entanto, Git aceita datas no futuro - veja meu filho Git. A propósito, também é possível criar pais solteiros.


Gráfico social


No gráfico social, também são armazenados outros eventos além do nascimento: batismo, mudança de residência, graduação, casamento, divórcio, morte, funeral. Depois da morte o ramo vai para o céu digital o aparecimento de eventos subsequentes, exceto funerais, é impossível no ramo. No servidor, você pode proteger esse ramo (não se preocupe: é possível "ressuscitá-lo" no futuro, se necessário).


O evento "Casamento" tem dois ancestrais - cônjuges. O "divórcio" tem um ancestral - o "casamento" anterior. Família e paternidade são trabalho, então podemos dizer que após o casamento também aparece um novo descendente - "relacionamento" que termina após o divórcio (ou a morte de um cônjuge). É retomado após o próximo casamento. Além disso, várias pessoas podem participar de um relacionamento (mesclando vários ramos).


Finalização


A cereja do bolo: fazemos um repositório de backup e carregamos todos os participantes no GitHub, GitLab ou em qualquer outro servidor que suporte o Git. Podemos empurrar os galhos um por um, mas usando o comando mágico , empurraremos todos, o que é muito mais rápido e simples:


 git remote add origin https://gitlab.com/KvanTTT/Family.git git push origin --all -u 

Para gerar uma árvore genealógica comum, você precisa passar a bandeira --only-birth-events ao iniciar o gerador. Nesse caso, um commit por pessoa (nascimento) será criado. Caso contrário, um rede social gráfico social será gerado.


Exemplos


Como um pequeno exemplo, que pelo menos funcionará em todos os lugares, criei minha árvore genealógica, e um grande exemplo é a árvore dos presidentes dos EUA (2145 pessoas). Eles estão disponíveis nos repositórios Kochurkins e Presidents , respectivamente. Para criar minha própria árvore, usei o serviço geni.com , do qual exportei a árvore para o GEDCOM. Um script gerado para criar um repositório genealógico está disponível no Gist .



No GitHub (e também no GitLab), você pode navegar pelos ancestrais e descendentes. Isso é semelhante aos sistemas wiki genealógicos Familypedia ou WeRelate . No entanto, o GitHub / GitLab é mais avançado: as árvores são facilmente baixadas (com a ajuda do comando --clone ). E o mais importante, você pode abrir o gráfico inteiro de uma só vez. (Nos programas genealógicos existentes, por algum motivo, há dificuldades em abrir até pequenos gráficos.) E você pode fazer isso usando diferentes ferramentas (serviço web, Git Extesions , Sourcetree , GitKraken e outros). Além disso, esses serviços podem ser usados ​​gratuitamente, ao contrário da maioria dos serviços genealógicos.


Vale ressaltar que no GitHub / GitLab até mesmo algum tipo de análise está disponível: você pode descobrir quem tem mais seguiu a conta do Instagram vida agitada. Ou o mais público: a guia Insights exibe uma lista de pessoas em ordem decrescente de confirmações.



Infelizmente, o GitHub e o GitLab não exibem grandes árvores corretamente, mas elas são armazenadas corretamente - você pode abrir o repositório e verificar. Aqui está minha árvore na interface da web do GitLab:



Problemas


Não está muito claro como complementar a história desde as raízes. Por enquanto, você precisa gerá-lo desde o início, a partir do arquivo GEDCOM. Provavelmente, isso pode ser feito com a ajuda de rebase - você pode tentar contar nos comentários. Também seria melhor reescrever o código para torná-lo "orientado a confirmação", não "orientado a eventos", porque é mais parecido com o Git: na verdade, o ramo é uma sequência de confirmações, não uma entidade separada. Também pensei em implementar tags e submódulos , mas por enquanto não sei como fazê-lo melhor.


Conclusão


Se você estender a idéia de árvores genealógicas aos serviços da Web para desenvolvedores, usando problemas, poderá criar tarefas globais e distribuí-las de acordo com os marcos : infância, juventude, idade adulta, idade avançada.


Além das árvores genealógicas, você pode usar o Git para codificar árvores genealógicas das linguagens de programação (isso é ainda mais nerd), árvores de sintaxe e qualquer estrutura de árvore. O Git também pode ser útil para donas de casa para construir relacionamentos entre os personagens das novelas brasileiras :)


Benefício prático: esse aquecimento ajuda a entender melhor a estrutura do Git, seus comandos e o formato GEDCOM para descrever dados genealógicos.


As fontes do artigo estão disponíveis no GitHub - envie Pull Request se você encontrar algum erro ou quiser adicionar algo. Para converter para o formato habr.com, eu uso a biblioteca MarkConv .

Source: https://habr.com/ru/post/pt465959/


All Articles