Acelere a colaboração e o desenvolvimento ágil com componentização
Serviços de DevOps do Azure | Azure DevOps Server 2022 - Azure DevOps Server 2019
Seu produto é bem-sucedido, sua organização está crescendo e é hora de aumentar sua base de código para corresponder a esse sucesso. À medida que você expande 2-3 equipes que trabalham em uma única base de código em um único produto, você pode se encontrar fazendo perguntas como:
Como minhas equipes podem compartilhar componentes reutilizáveis de forma eficiente?
Como faço para permitir que minhas equipes de recursos iterem rapidamente sem interferir no trabalho de outras equipes?
Como posso dar autonomia às minhas equipas para iterarem ao ritmo certo para elas?
As equipas, em qualquer fase, podem beneficiar da consideração destas questões. Se você é uma equipe estabelecida com uma base de código legada, pode estar fazendo essas mesmas perguntas enquanto lhe pedem para entregar mais valor, mais rápido do que nunca. Independentemente da sua situação, a componentização pode ajudá-lo a criar uma base de código que se adapte ao tamanho da sua equipe e à velocidade do desenvolvimento atual.
Neste artigo, exploramos como a composição binária por meio dos Artefatos do Azure pode ajudá-lo a gerenciar e compartilhar suas dependências externas, seu software de código aberto e seus componentes compartilhados isolados.
Componentes e composição
A componentização é o processo de dividir e organizar o seu produto em componentes distintos. A maioria dos projetos .NET já tem alguma noção de componentes na forma dos projetos dentro da solução. Por exemplo, um site básico pode consistir em um componente front-end, um componente de acesso a dados e um componente de modelo/armazenamento de dados.
Composição da fonte
À medida que o seu produto cresce, a solução e o modelo de projeto podem tornar-se ineficientes. As alterações levam mais tempo para serem integradas e são mais difíceis de mesclar, a compilação fica mais lenta e os componentes começam a crescer de um único projeto para vários projetos. Geralmente, este é o ponto em que as equipes começam a dividir esses conjuntos de projetos relacionados em soluções separadas.
Depois de superar uma única solução, como você cria componentes se torna uma questão interessante. Começamos com a composição de código-fonte, onde cada componente é referenciado por meio de uma referência de projeto no Visual Studio. A composição do código-fonte é possível desde que seu código-fonte viva em um único limite de composição: uma única solução dentro de um único repositório de origem.
Infelizmente, essas referências de projeto começam a quebrar quando várias soluções estão envolvidas. Neste ponto, quando a solução A depende da solução B, ela deve se referir aos binários construídos (como DLLs) produzidos pela solução B - esta é a composição binária.
Assim, esses binários agora precisam ser criados e disponibilizados para a solução A antes que ela possa ser compilada com êxito. Existem algumas maneiras de fazer isso:
Você pode verificá-los no controle do código-fonte. Dependendo do seu sistema de controle do código-fonte, os binários podem aumentar rapidamente o tamanho do seu repositório, diminuindo os tempos de check-out e o desempenho geral do repositório. Se você começar a trabalhar em ramificações, várias equipes podem acabar introduzindo o mesmo binário em versões diferentes, levando a conflitos de mesclagem desafiadores.
Como alternativa, você pode hospedá-los em um compartilhamento de arquivos, embora essa abordagem tenha certas limitações. Os compartilhamentos de arquivos não têm um índice para pesquisas rápidas e não fornecem proteção contra a substituição de uma versão no futuro.
Composição da embalagem
Os pacotes abordam muitos dos desafios de referenciar binários. Em vez de verificá-los na fonte, você pode fazer com que uma solução B produza seus binários como pacotes NuGet que outra solução A pode consumir. Se a solução A e a solução B forem mantidas como componentes separados, onde as mudanças simultâneas em A e B são raras, a composição do pacote é uma ótima maneira de gerenciar a dependência de A em B. A composição do pacote permite que B itere em sua própria cadência, enquanto A é livre para obter atualizações de B quando o cronograma de A permitir, e permite que várias equipes iterem e atualizem a solução B sem afetar a solução A (ou outras soluções C ou D).
No entanto, a composição das embalagens tem o seu próprio conjunto de desafios. Até agora, examinámos um exemplo simples. Dimensionar a composição do pacote até o tamanho de uma base de código grande (algo como Windows ou Bing) pode causar uma série de desafios:
Compreender o impacto de quebrar mudanças em um componente baixo no gráfico de dependência torna-se muito desafiador.
As dependências diamantadas podem se tornar um obstáculo significativo para a agilidade. Em uma dependência de diamante, os componentes B e C dependem de um componente compartilhado A, enquanto o componente D depende de B e C. Quando o componente A introduz uma nova versão com alterações de quebra, se B atualiza para a nova versão, mas C não, D não pode receber as atualizações de B sem introduzir um conflito de dependência. Neste exemplo simples, uma conversa com C pode ser tudo o que é necessário para resolver o conflito. No entanto, num gráfico complexo, os diamantes podem rapidamente tornar-se insolúveis.
Quando as modificações precisam ser aplicadas a dois componentes que são compostos usando pacotes, o ciclo de iteração do desenvolvedor torna-se consideravelmente mais lento. Se o Componente A for atualizado, será necessário reconstruí-lo, reempacotá-lo e republicá-lo. Posteriormente, o componente B deve atualizar para a versão publicada recentemente para validar a alteração feita no componente A. Empregar a composição do código-fonte, que permite a construção simultânea do componente A e B, proporcionará consistentemente um ciclo de iteração mais rápido para os desenvolvedores.
O que deve utilizar
Em geral, vimos grandes equipes serem mais bem-sucedidas quando usam uma mistura de estratégias de composição. Para ajudar a determinar o que é certo para sua base de código, comece mapeando o gráfico de dependência do seu produto e comece a agrupar seus componentes em conjuntos de componentes relacionados.
Por exemplo, você pode ter uma coleção de componentes constituindo sua estrutura e outro conjunto de componentes formando seu serviço voltado para o usuário. Em seguida, para cada grupo de componentes relacionados, faça estas perguntas:
Posso antecipar check-ins frequentes nos conjuntos que estabeleci para as minhas equipas?
Uma única equipa é responsável por todo o conjunto?
Para um único conjunto, existe uma cadência de lançamento compartilhada?
Em nossa experiência, descobrimos que o uso da composição de fontes é mais eficaz para projetos relacionados tratados por uma única equipe ou um grupo de equipes relacionadas. Por outro lado, a composição binária se mostra vantajosa para software de código aberto, dependências externas (componentes de equipes distantes ou isoladas) e componentes compartilhados independentes.