fbpx
Abstrações – Tradeoffs e co-responsabilidade
Publicado em: sábado, 20 de abr de 2019
Categorias: Arquitetura | Novidades

Embora a prática seja linda, é hora de falarmos de algo abstrato: as próprias Abstrações.

Primeiro preciso lembrar que essa é uma opinião pessoal, fruto das diversas experiências, criando ou consumindo abstrações das mais diversas em projetos de todos os tamanhos.

O que é uma abstração?

Uma abstração é em geral um conjunto de classes/componentes/serviços correlatas que exercem o papel de simplificar uma implementação em nome de um objetivo palpável.

Confuso?

  • Um ORM tem o objetivo de simplificar a implementação do acesso a dados mapeando seus objetos e suas tabelas ou views correlatas no banco de dados.
  • WCF tinha o objetivo de simplificar a implementação de diversos protocolos e transportes na exposição de serviços que facilitassem a computação distribuída.
  • ASP.NET Core tem o objetivo de simplificar, padronizar e otimizar a entrega das principais demandas para a construção de aplicações web e API’s HTTP, multiplataforma de forma testável.
  • SignalR é uma biblioteca open source que simplifica a adição de funcionalidades real-time em web apps, habilitando o envio de notificações push para seus clientes.

Abstrações simplificam e encapsulam algo. Cada abstração tem um propósito diferente, abstrações da mesma coisa tem propósitos diferentes. Vejamos o ADO.NET, que abstrai a complexidade dos protocolos binários de comunicação com as diversas tecnologias de banco. Por outro lado, temos Dapper, que abstrai o ADO.NET. Mas se voltarmos vamos ver a CLR ou o .NET Core, abstraindo o sistema operacional e suas libraries base, ou ainda o .NET Standard abstraindo as diversas e complexas versões dos runtimes .NET ao redor do ecossistema, suportando .NET Core, Mono + Xamarim, Web Assembly (mono).

Nós programamos o dia todo sob abstrações de abstrações… de abstrações…

Mas nós também criamos nossas abstrações. Umas mais elegantes, e outras menos. Umas baseadas em padrões, outras pela nossa própria percepção de um padrão, seja lá qual for o motivo, as vezes conseguimos trazer alguma simplificação para o contexto de um problema do dia-a-dia. Seja pelas vias “formais” ou por pura intuição, talvez preguiça, ou pura iluminação divina dos deuses da programação, aplicamos abstrações para alcançar objetivos de forma mais fácil.

Não importa o quão você queira otimizar, você no mínimo estará sob uma abstração, criando outra abstração. Afinal seu software abstrai a complexidade de realizar tarefas de negócio, realizar operações em bancos e tabelas, para que um usuário tenha um formulário bonitinho para interagir. Em casos mais complexos, como um e-commerce, seu software está abstraindo a complexidade de escolher um produto, comprar, e pagar, independente da loja física e seu estoque, independente da distância, podendo fazer isso de casa, do trabalho, ou no celular, no intervalo de alguma tarefa. Abstrações existem para simplificar o uso/consumo de algo!

Abstrações são boas?

As abstrações são boas quando cumprem bem o seu papel.

Mas quando elas não são boas?

Poderia parecer óbvio, com base no tópico anterior e a resposta clichê seria: Quando não cumprem bem o seu papel.

Sim, esse de fato é um caso, mas há outro caso em que uma abstração não é boa: Quando é empenhada no contexto errado.

Você já tentou rebater uma bola de basquete com uma espada samurai (Katana), usando o fio da lâmina para o feito?

Eu vejo essas coisas acontecendo nos projetos que sou chamado para olhar, inspecionar, avaliar, ajudar. São abstrações empenhadas em cenários errados. Claro que não é maioria, na maior parte dos casos esse não é o problema, mas é relativamente comum encontrar esse problema quando alguém chega ao ponto de “travar” ou “não conseguir fazer” ou até “não conseguir pensar”.

Um exemplo?

Na série sobre RabbitMQ eu fiz um post sobre o uso equivocado do Redis como Message Broker. O Redis é ruim? Não!!!! Nunca disse isso. O pub/sub do Redis é ruim? Não, não disse isso. O que disse é que, se você quer usar de forma a empenhar nele a responsabilidade sobre resiliência, você está construindo um castelo sobre terreno arenoso. Ele não vai entregar o que você quer e você e seu projeto capotarão juntos.

Mas então, onde e quando usar?

Qualquer cenário em que se o Redis cair ou a máquina/container/serviço sofrer um reboot e a perda das mensagens nesse meio tempo não afetar sua operação. Pensa nele como cache, ou storage de configurações e notificação de mudança de configuração. Ou caching e notificação de update no cache.

Outro exemplo, é o uso de MicroORM’s e ORM’s em decisões unilaterais a favor de apenas um deles. Perdas e ganhos não são avaliados e como resultado vemos aumento no custo de desenvolvimento, não necessariamente evolução na qualidade, ou perda de performance em cenários triviais.

Você não pode usar uma abstração sem necessariamente saber/compreender como e o que ela faz!

Quem já direcionei de perto sabe que fundamentar o entendimento sobre algo é uma exigência básica. Sou chato com isso (e com outras milhares de coisas). Conhecer bem os alicerces daquilo que são pilares da sua arquitetura faz toda a diferença. Não faltaram oportunidades na carreira de demonstrar o valor dessa abordagem. Acredito que essa abordagem separa os meninos dos homens, amadores de profissionais. Claro que como qualquer pessoa normal, faço escolhas, priorizo assuntos em detrimento de outros, no entanto eu também escolho assuntos onde eu quero estar completamente familiarizado, não somente com o uso, mas sobre como aquilo funciona, de ponta-a-ponta. E isso faz muita diferença.

Essa abordagem me dá segurança para tomar melhores decisões, e eventualmente sou apresentado a formas diferentes de resolver problemas: problemas conhecidos e problemas que nunca tive/vivenciei. Nesse último exemplo, em que esbarro em problemas que nunca tive, eu de fato tento entender o que causou/exigiu aquela solução, e esse é um aprendizado muito especial, pois não tenho a pressão de um problema a resolver, e ainda assim estou diante de uma solução de alguém que o vivenciou de fato.

Se está confuso, não se assuste eu no futuro irei relacionar esse post aqui a cada vez que me deparar com exemplos.

Por hora é como me relaciono com o estudo e compreensão de Service Mesh com Istio e Envoy, principalmente no Envoy como Sidecar.

Portanto, minha regra para o consumo de uma abstração é: Saiba trabalhar sem ela, entenda como as coisas funcionam, entenda as possibilidades de uso sem sua abstração e entenda o que ela abstrai, como abstrai e como ela pode simplificar sua vida. Não ignore conhecimento específico, pois você não veio ao mundo para ser conduzido pela tecnologia. Se você está lendo esse post completamente conceitual, creio que você está em busca de entender uma ideia, e isso difere você de mais da metade da comunidade, que só busca a resolução de problemas. Assim meu conselho para você é continuar a buscar o discernimento necessário para conduzir a tecnologia a favor dos seus objetivos técnicos.

Conclusão

  • Abstrações não são nem boas nem ruins (há exceções).
  • Saiba como usar, quando usar e como tirar proveito de uma abstração para simplificar tarefas complexas, principalmente tarefas repetitivas.
  • Lembre-se que abstrações possuem propósito finito e restrito, e não necessariamente estão de acordo com suas necessidades.
  • Não se esqueça de que abstrações simplificam algo, e portanto essa simplificação merece a devida atenção para compreender até que ponto ela te aproxima ou te distancia de seu objetivo de negócio.
  • Você só saberá decidir bem, conhecendo a tecnologia abstraída com o mínimo de profundidade.

No próximo post eu falo sobre como eu crio minhas abstrações, mostrar alguns exemplos. Eu tenho uma dúzia de regras para isso.

O Cloud Native .NET é meu principal projeto.

Onde empenho energia para ajudar, acompanhar, direcionar Desenvolvedores, Líderes Técnicos e jovens Arquitetos na jornada Cloud Native.

Conduzo entregando a maior e mais completa stack de tecnologias do mercado.

Ao trabalhar com desenvolvedores experientes, eu consigo usar seu aprendizado com .NET, banco de dados, e arquitetura para encurtar a jornada.

Ao restringir à desenvolvedores .NET eu consigo usar do contexto de tecnologias e problemas do seu dia-a-dia, coisas que você conhece hoje, como WCF, WebForms, IIS e MVC, por exemplo, para mostrar a comparação entre o que você conhece e o que está sendo apresentado.

É assim que construímos fundamentos sólidos, digerindo a complexidade com didática, tornando o complexo, simples.

É assim que conseguimos tornar uma jornada densa, em um pacote de ~4 meses.

Eu não acredito que um desenvolvedor possa entender uma tecnologia sem compreender seus fundamentos. Ele no máximo consegue ser produtivo, mas isso não faz desse desenvolvedor um bom tomador de decisões técnicas.

É preciso entender os fundamentos para conseguir tomar boas decisões.

0 comentários

Enviar um comentário

O seu endereço de e-mail não será publicado. Campos obrigatórios são marcados com *

Esse site utiliza o Akismet para reduzir spam. Aprenda como seus dados de comentários são processados.

Luiz Carlos Faria

Mensagem do Autor

Espero que goste desse post. Não deixe de comentar e falar o que achou.

Se acha que esse post pode ajudar alguém que você conheça, compartilhe!

 

Lives

Fique de olho nas lives

Fique de olho nas lives no meu canal do Youtube, no Canal .NET e nos Grupos do Facebook e Instagram.

Aceleradores

Existem diversas formas de viabilizar o suporte ao teu projeto. Seja com os treinamentos, consultoria, mentorias em grupo.