Desenvolver software tornou-se uma atividade complexa! Não basta apenas codificar e entregar, é necessário compreender a fundo as necessidades, conhecer as diversas possibilidades de como arquitetar um software e fazer escolhas que poderão ser determinantes para viabilizar e facilitar sua evolução e manutenção.
E uma pergunta comum é: há uma arquitetura melhor? Há uma arquitetura de software ideal?
Para quem ainda se apaixona por tecnologias do momento, a resposta pode ser tendenciosa e muitos poderão dizer: “sim, há uma arquitetura melhor e ela é a …”.
Mas para aqueles que já conhecem e implementaram inúmeras arquiteturas, a resposta natural é: depende!
Para chegar a uma resposta normalmente olhamos para o que conhecemos e para o que o mercado e comunidade dizem ser bom, normalmente focamos nas coisas legais de aspectos puramente técnicos e fazemos escolhas que podem não gerar um resultado satisfatório a médio e longo prazo. Temos uma tendẽncia à olhar o que há de bom ou ruim em usar por exemplo: monólitos, microservices, orientação a eventos, server-side, camadas, spa, componentes, dentre tantas outras, e esquecemos de associar isso ao momento e necessidades reais dos projetos.
Pense em uma casa que você deseja construir ou reformar. Se você tivesse total liberdade de escolha e recursos infinitos certamente você desejaria um tipo de casa com um tipo de arquitetura. Mas haveria decisões sobre a arquitetura da casa que poderiam ser conflitantes, como desejar um estilo rústico ou moderno, funcional ou luxuoso, etc…
Adicione a isso limitações para a escolha como já existir um espaço determinado pelo terreno e relevo, um limite de recursos, regras determinadas para se construir em determinado local/região. Ou seja, as escolhas arquitetônicas de uma casa não levam em conta apenas as preferências de quem está escolhendo.
Em um software ocorre o mesmo, há cenários além da arquitetura em si que determinam qual poderá ser a mais adequada.
A sequência deste artigo não foca nos pontos positivos e negativos de microservices, se monólito ainda faz sentido ou não, vantagens de orientação a eventos, uso de camadas, etc. Já há materiais publicados com esses detalhes. Esse artigo foca nas ponderações que você pode fazer durante a escolha da arquitetura, para que tal escolha seja a melhor para o seu cenário e necessidades.
Modelo e visão de negócio.
Você possui total conhecimento do modelo e visão de negócio da solução? Já considerou as perguntas a seguir?
Qual o público alvo?
Isso pode ser determinante na adoção ou não de arquiteturas distribuídas, cliente-servidor, baseadas em cloud, etc.
Estamos acostumados a clientes com total conectividade a internet, familiarizados com browsers, smartphones, porém isso não é uma regra.
Ainda há públicos com baixa conectividade, seja por zonas rurais, edificações que limitam o sinal, ou até o custo de acesso. Para públicos assim pode ser inviável softwares distribuídos, onde um mobile app ou um web frontend acessem vários serviços trafegando grandes pacotes de dados. Situações assim precisam de arquiteturas com foco em “offline first”, que reduzam a dependência do cliente de estar conectado o tempo todo para usar o software.
Há públicos que irão demandar constantes consultas e/ou relatórios que avaliam uma grande massa de dados em tempo real. Isso pode tornar inviável o uso de consultas sobre serviços/bases focadas nas rotinas operacionais, ou ainda dados segregados em diversos locais demandando um excesso de requisições para união e consolidação de dados. Isso torna necessário pensar em replicação e reorganização de dados, concorrência, cache, garantia de consistência, processos assíncronos para execução de consultas e geração de relatórios, etc. E tudo isso mantendo uma usabilidade para o cliente que ofereça a ele experiência de tempo real.
Há públicos que usam a solução em momentos críticos, onde o software não pode errar ou estar indisponível. Casos assim não podem simplesmente retornar um erro ao usuário informando “Tente mais tarde”. Isso torna necessário pensar em arquiteturas de alta disponibilidade e resilientes, que consigam lidar com erros e refazer o processo a ponto de finalizar a operação desejada pelo cliente.
A melhor arquitetura é aquela que viabiliza o total uso da solução perante as necessidades e condições do público alvo.
Qual o momento da solução? É uma POC, Protótipo, MVP ou crescimento e escala?
Isso influencia diretamente no nível de complexidade a ser considerado para a arquitetura. Arquiteturas distribuídas e escaláveis normalmente serão mais complexas de implementar e manter, isso pode afetar o tempo de validação/lançamento.
Em uma POC, protótipo ou MVP, escolher arquiteturas que o time ainda não domine também podem fazer com que um tempo valioso do projeto seja gasto em detalhes puramente técnicos, atrasando projetos e comprometendo a estratégia do produto/solução. Nesses casos é importante optar por iniciar com arquiteturas mais simples, que centralizam o desenvolvimento e execução do software a fim de facilitar rápidas implementações e entregas. Monólito e/ou server-side nestes cenários ainda possuem aplicabilidade.
Já quando um software entra em fase de crescimento e escala é que se torna necessário reorganizar a arquitetura. O que normalmente leva a escolhas de arquiteturas distribuídas como: microservices, uso de eventos, segregação de dados, microfrontends, etc. Isso trará maior complexidade de infraestrutura, gestão de dependências, dentre outros, mas facilitará a escala. É importante entender que a cadência de entrega e pontos de gargalos podem sofrer alterações, e isso é normal e um fator inevitável do crescimento e escala.
A melhor arquitetura é aquela que proporciona equilíbrio entre facilidade e velocidade de implementação e entrega vs capacidade de crescimento e escala considerando o momento do projeto e solução.
Qual a forma de comercialização, obtenção de clientes e faturamento?
Isso influencia diretamente na forma como um software será distribuído e nas ações necessárias para inclusão de novos clientes para utilizar a solução, o que por consequência reflete em decisões arquiteturais.
Se a solução for comercializada em modelo SaaS, algumas arquiteturas são indicadas, normalmente seguindo a linha de arquiteturas distribuídas, se for em modelo on-premisses, outras arquiteturas podem ser mais adequadas como monólitos.
Se para cada cliente a arquitetura prever o provisionamento de infraestruturas como base de dados, instâncias próprias ou bucket de arquivos, poderá haver dificuldades para inclusão de novos clientes já que a arquitetura da solução pode obrigar o envolvimento direto do time técnico de infra e/ou devs.
Se a arquitetura da solução não permitir processos simplificados de acompanhamento de uso da solução ou bilhetagem de consumo de recursos, poderá haver dificuldades periódicas em faturar e cobrar o cliente.
A melhor arquitetura é aquela que permite a inclusão de novos clientes e cobrança de uso da solução sem envolvimento de times técnicos.
Além do cliente, quais outros atores envolvidos na operação da solução?
Isso influencia em como atores internos poderão interagir com a solução. É comum haver necessidade de áreas da empresas como vendas, implantação, suporte, financeiro, dentre outras, tenham necessidades de executar ações na solução e a arquitetura do software precisa possibilitar que atores diferentes dos clientes possam executar tais ações, sendo elas muitas vezes com permissões e visibilidade de escopos de dados diferentes da dos clientes.
Questões como autenticação e autorização, aspectos de segurança, escrita e leitura de dados, estão atreladas a essas necessidades e são influenciadas por escolhas arquiteturais. Por vezes se torna necessário criar camadas que trabalhem estes aspectos e tais camadas precisam estar em conformidade com a arquitetura escolhida.
A melhor arquitetura é aquela que permite a fácil adaptação do software à inclusão de novos atores/perfis de uso.
O modelo de domínio.
Conhecer o modelo de domínio da solução possibilita entender o tamanho que o software poderá ter, assim como cada parte da solução poderá ser organizada. É importante visualizar se a solução proposta foca em um ou vários domínios de negócio, os contextos existentes em cada domínio e a quantidade e relevância das entidades em cada contexto, assim como entender como elas se relacionam.
Em arquiteturas monolíticas isso é essencial para a forma como serão organizados os módulos e os níveis de acoplamento entre eles, inclusive possibilitando posteriormente fragmentações do monólito para arquiteturas distribuídas.
Em arquiteturas distribuídas, o modelo de domínio é vital para fragmentar a solução em partes de tamanho adequado e coesas, e na decisão de como essas partes irão se comunicar e qual será o nível de acoplamento. Mais importante que usar microservices por exemplo é entender que domínio/contexto ou conjunto de features um microservice agrupa, e como eles conversam uns com os outros, sejam por chamadas explícitas ou através de eventos.
A melhor arquitetura é aquela que possibilita por si só visualizar os domínios, contextos e até entidades, e não apenas aspectos técnicos como estilos e padrões arquiteturais.
Integração com terceiros.
A forma como um software terceiro está arquitetado e implementado não deve interferir diretamente na arquitetura do seu software. Deve-se estar atento aos limites entre os softwares e escolher arquiteturas que permitam o adequado isolamento destas integrações.
Se a solução possui integrações com terceiros, é importante que essa questão esteja prevista na arquitetura e em como será implementada na solução, pois a médio prazo é comum que exista alteração na forma de integrar com estes terceiros ou ainda a troca do próprio terceiro.
Se outros sistemas poderão estar integrados à solução, é importante que a arquitetura esteja estruturada para expor pontos de integração sem que estes interfiram na implementação focada em negócio.
A solução não pode estar arquitetada de forma que mudanças de terceiros tenham grandes impactos na solução, ou que cheguem até ao ponto de inviabilizar o funcionamento da mesma se houver a necessidade de trocas de terceiros.
A melhor arquitetura é aquela que permite o software se integrar a terceiros e terceiros se integrar ao software sem a necessidade de refatorações ou mudanças em código associado ao negócio.
Cadência no lançamento de funcionalidades e versões.
Dentre as várias arquiteturas de software possíveis há aquelas que facilitam o lançamento de funcionalidades e versões de forma mais rápida ou aquelas que demandam um planejamento e tempo de execução maior para o lançamento. Neste sentido é importante um alinhamento fino entre as necessidades e expectativas de produto para que escolhas de arquitetura não impactem na cadência de entrega.
Quando a arquitetura obriga o time a aguardar a conclusão da implementação de grandes quantidades de código para entregar algo em produção, ela impede que times trabalhem paralelamente, cada um no seu ritmo.
A melhor arquitetura é aquela que permite novas funcionalidades e versões sem grande esforço coletivo de mudanças no software e sincronização de trabalho.
Conhecimento e expectativa de crescimento do time.
A escolha de uma arquitetura para um software que possuirá clientes reais deve levar em conta o conhecimento do time sobre ela. Sempre que adotamos uma nova arquitetura surgem questões a serem aprendidas, experimentadas e validadas. Isso tem um custo e precisa estar claro ao time. Dependendo do momento do projeto/solução, escolher arquiteturas que o time ainda não possui conhecimento pode determinar o fracasso na implementação.
Além disso, conforme crescimento do time, algumas arquiteturas inviabilizam o trabalho paralelo de muitos(as) devs, o que normalmente gera a necessidade de gastar tempo com gerenciamento e sincronização de trabalho, ou ainda tempo ocioso de alguns times enquanto aguardam outros concluírem suas implementações. Com o crescimento do time, algumas mudanças arquiteturais não estarão focadas diretamente na execução do software, mas em como manter a viabilidade de que vários(as) devs possam paralelamente trabalhar sobre a solução.
A melhor arquitetura é aquela que permite muitos(as) devs trabalharem paralelamente na evolução e manutenção do software.
Orçamento para implementação e execução do software.
A arquitetura escolhida para um software influencia no tempo gasto para implementação e em como este será implantado e executado. Conhecer o orçamento disponível é essencial para que sejam feitas escolhas de arquiteturas que o custo se encaixa em tal orçamento.
Escolhas de arquiteturas que parecem ser adequadas a todas as demais questões mas que não se encaixam no orçamento podem decretar o fracasso durante a fase de implementação ou depois durante a execução e uso do software pelo cliente. Tudo tem um custo, e este custo deve ser pago através do próprio uso da solução pelo cliente. Quando a implementação e manutenção da solução no ar ficar mais cara que o ganho financeiro que ela traz, a mesma estará mais próxima de seu fim.
A melhor arquitetura é aquela cujo custo de desenvolvimento e execução se pague através do uso do software pelo cliente.
Escolher a “melhor arquitetura” para seu projeto sem levar em conta os pontos apresentados, pode funcionar, mas provavelmente gerará dificuldades e questionamentos ao longo do tempo. Esteja ciente de que a escolha de uma arquitetura não leva em conta apenas as vantagens sempre destacadas em cada uma, muito menos deve ser feita considerando apenas o gosto pessoal de quem define ou ainda o desejo de simplesmente aprender e implementar algo em uma determinada arquitetura.
A escolha da arquitetura poderá influenciar o trabalho de muitas pessoas, durante muito tempo, então ela precisa ser feita considerando motivações claras e alinhadas com questões como as citadas acima.
O software com a “melhor arquitetura”, mas que não esteja alinhado aos pontos apresentados, tende ao fracasso, pois um software difícil de implementar e manter, que não atende a todas necessidades do cliente, que tem alto custo e por fim não se paga, normalmente se torna o indesejado “software legado “.
Por fim, algumas ponderações adicionais a serem feitas durante a definição de uma arquitetura:
-
Não escolha uma arquitetura em função de frameworks ou ferramentas. Escolha frameworks e ferramentas alinhados a arquitetura definida!
-
Normalmente os problemas que indicamos ser arquiteturais, são apenas de código desorganizado e altamente acoplado. Qualquer arquitetura cujo código esteja desorganizado e altamente acoplado irá gerar dificuldades para manutenção e evolução.
-
Pensar em arquitetura não é uma atribuição apenas de arquitetos de software, todo(a) desenvolvedor(a) deve se preocupar com arquitetura.
-
Evite utilizar projetos reais para aprender novas arquiteturas. Primeiro aprenda as arquiteturas desejadas em pocs ou projetos exemplares e depois identifique qual melhor projeto e momento onde utilizá-las.
Sobre algumas arquiteturas atuais e/ou tradicionais:
-
Microservices é uma ótima arquitetura, mas traz complexidade para construção, orquestração, segurança, resiliência, dentre outros. Isso requer conhecimento e ferramentas que por vezes geram alto custo.
-
Monólito ainda tem aplicabilidade, essa arquitetura não é uma vilã, mas dificilmente se encaixa para soluções que estão em fase de crescimento e escala, e normalmente a causa é o código desorganizado e acoplado.
-
Uso de camadas normalmente é feito em conjunto com vários outros estilos e padrões arquiteturais, porém mesmo sendo tão utilizado, ainda é comum haver falhas no seu uso, destacando-se o código e responsabilidades fora da camada adequada, o que torna o software desorganizado e de difícil manutenção.
-
Orientação a eventos possui várias vantagens que ajudam no desacoplamento, mas requer disciplina e organização sobre os contratos relacionados aos dados contidos em um evento e no mapeamento de quem publica e consome tais eventos.
-
Fragmentação do modelo de dados é importante para grandes soluções e arquiteturas distribuídas, mas impacta em rotinas que consultam fontes distintas passando por protocolos que não permitem velocidade na busca e agregação dos dados. Há cenários onde ainda é necessário centralizar os dados (podendo estes ser um espelho das fontes originais).
E, como resposta a pergunta do título deste artigo:
- A melhor arquitetura é aquela que permite entregar software, em um tempo hábil, que gere valor ao cliente e que permita a escala conforme necessidade e momento.
A imagem principal foi composta a partir de ilustrações de: Fundo vetor criado por macrovector - br.freepik.com