Technology Radar

Sobre o Radar

Nossa ideia ao criar esse radar era divulgar sobre ferramentas, práticas e processos que acreditamos. O oposto também é válido: divulgar tudo aquilo que, por algum motivo, não acreditamos mais.

Todo o conteúdo deste documento é fortemente baseado na experiência e conhecimentos dos nossos colaboradores. Mas como qualquer discussão em engenharia de software, não há uma resposta única e exata. Antes de seguir o que está escrito aqui, o leitor deve analisar bem o contexto em que está envolvido.

Nosso tech radar usa o formato definido e utilizado pela Thoughtworks em seus radares.

É importante que o leitor entenda como esse radar funciona. Os ítens foram classificados em práticas, ferramentas, plataformas, linguagens/frameworks. Cada uma dessas categorias encontra-se em uma das extremidades do radar.

Além disso, cada ítem foi colocado em um anel, de acordo com nossa opinião. Os anéis são:

Adopt / Adote
Nós acreditamos que esses ítens podem ser adotados pela indústria. Acreditamos que a escolha desses ítens é, na maioria das vezes, acertada.
Trial / Experimente
Vale a pena testar em projetos menores ou com baixa criticidade.
Assess / Explore
Deve ser explorados com o objetivo de ver como se encaixa em sua empresa.
Hold / Evite
Os ítens que estão aqui devem ser evitados.

Esta é a primeira vez que nos organizamos para gerar tal documento. Temos muito ainda a aprender sobre ele, e portanto, todo feedback é bem vindo.

Técnicas

Microservices

A quebra de um programa em diversas partes é uma das grandes discussões de modelagens. Em uma granularidade maior e pensando em responsabilidades distintas é possível dividir um sistema em outros menores. Mas com o passar do tempo percebemos empiricamente que a manutenção de tais sistemas fica cada vez mais complicada. A quebra em micro serviços é uma possibilidade que tem sido mais discutida nos últimos anos. Mas otimizar uma variável (no caso, o tamanho de cada serviço) pode complicar outra variável (por exemplo, a complexidade da comunicação). Se o que mais dói na evolução dos serviços é a evolução do protocolo de comunicação, há indícios de que seja interessante minimizar a complexidade da comunicação. Não estamos falando do uso de um formato mais simples, mas de minimizar a variedade (os tipos) de comunicações entre os sistemas. Se cada um deles é relativamente pequeno e auto-contido, a interface de comunicação pode ser mais simples e estável - e este pode ser um bom caminho para quem pretende trabalhar com serviços, independente de serem micro ou macro.

UX ágil e Lean UX

Não é difícil encontrar casos de sucesso de implementações de Lean UX, a colaboração de toda a equipe no processo de criação de protótipos e a coleta constante do feedback dos usuários prometem garantir o melhor design para o produto. A ideia de se ter feedback constante do usuário final, prototipação no navegador (movimento NoPSD) são bastante interessantes. Porém, a implementação de Lean UX em ambientes de desenvolvimento ágil é ainda um grande desafio. O tempo, os processos necessários e os esforços dos integrantes da equipe são distribuídos de forma bem diferente. Para satisfazer essas necessidades são necessárias adaptações das práticas ágeis com as quais a equipe já está acostumada e que nem sempre são viáveis. Nosso conselho, portanto, é para que sua equipe comece a pensar em práticas ágeis também para a área de usabilidade.

Client side MV*

Um dos maiores problemas enfrentados em aplicações web atualmente é lidar com diferentes versões de dados no cliente e no servidor. Cuidar da sincronização de todos esses dados por conta própria é bastante penoso e, por isso, surgiram, nos últimos tempos, diversas bibliotecas que procuram abstrair esse trabalho. Backbone talvez seja a mais conhecida atualmente e a primeira a ganhar tração no mercado. Porém, acreditamos que a abordagem seguida por ela não é tão efetiva quanto poderia ser: ainda é necessário escrever muito código para configurar a manipulação dos dados e a sua relação com a interface. Já as bibliotecas Ember e AngularJS apresentam uma abordagem declarativa bastante simples e parecem ser o caminho a se seguir para tratar desse problema.

Técnicas de disseminação de conhecimento

Concentração de conhecimento gera diversos tipos de desperdício em um time: retrabalho, stress, dependência de uma pessoa, que é "o único que sabe disso". E, felizmente, disseminar conhecimento é algo bastante simples e há diversas técnicas já bem conhecidas e documentadas para isso. Recomendamos conhecer e verdadeiramente aplicar práticas como hack days, brown bags (ou, como gostamos de chamá-los "Almoços Técnicos"), dojos e práticas ágeis do dia-a-dia de projetos, tais como, programação pareada e code review. Uma boa forma de começar a aplicar essas práticas no seu ambiente é propor um hack day, preferencialmente um que envolva todos os desenvolvedores da sua empresa com o objetivo de melhorar algo no próprio desenvolvimento ou na empresa como um todo.

Métricas de Código

Temos gostado cada vez mais de fazer uso de métricas de código para encontrar trechos de código deficientes no sistema. Elas são geralmente uma forma barata de detectar problemas. Em nossa opinião, todas as métricas são bem vistas; elas erram, mas acertam bastante também. Existem diversas ferramentas que as calculam, como é ocaso do Eclipse Metrics, JDepend, e etc. O problema é que elas são difíceis de serem utilizadas juntas. Hoje temos usado uma ferramenta própria.

DevOps

Os desenvolvedores precisam estar atentos a todos os pontos de falha que um software pode ter e isso vai muito além dos tradicionais bugs que o sistema pode ter. A infraestrutura da aplicação é um ponto importante nisso e os desenvolvedores que conhecem aspectos importantes disso levam muita vantagem na resolução desses problemas. Saber configurar um servidor, customizar de acordo com as necessidades do projeto e corrigir problemas de infraestrutura, além de aumentar o senso de responsabilidade da equipe sobre o sistema em questão, traz maior versatilidade do time e uma fonte de experiência para projetos futuros.

Visualização mobile de sites

O crescimento do mercado mobile é gigantesco em todo o mundo. No Brasil, a penetração de smartphones e tablets no mercado é um pouco mais lenta, mas tem crescido a passos largos, impulsionada por iniciativas governamentais, produção local de aparelhos, popularização do 3G, início do 4G e oferta de aparelhos bons cada vez mais baratos. Nesse cenário, acreditamos que a Web tem um papel fundamental. Acreditamos na estratégia "Web First", deixando a construção de aplicativos nativos em segundo plano e apenas em cenários onde são necessários e agregam real valor pro usuário e para a empresa. Acreditamos na Web acessível, multiplataforma e democrática. Por essa razão, recomendamos que se adote o design responsivo e outras técnicas de design adaptativo pra prover um único site, fluído e flexível, para todos os usuários. Entendemos que, como toda solução, o design responsivo tem suas limitações, mas acreditamos que seus benefícios fazem dessa técnica a melhor abordagem, ao invés da criação de sites mobile separados. Adotar a estratégia de um site único adaptável é a melhor maneira de estar preparado para a evolução da Web e dos dispositivos do futuro.

Práticas ágeis

Não é mais preciso argumentar sobre a utilidade de práticas ágeis, um sinal disso é que nem nos prestamos a dividí-las em seus vários sabores. Práticas ágeis reduzem o risco do seu projeto de diversas formas:
  • Desenvolvimento incremental permite que o cliente dê feedback mais cedo;
  • Integração contínua reduz tempo perdido com merges e garante o feedback dos testes automatizados;
  • One-click deploy reduz as chances de erro e incentiva deploys mais frequentes;
  • Code review e programação pareada aumenta a responsabilidade coletiva pelo código, a manutenção dos padrões do time, reduz a incidência de bugs e acelera o processo de aprendizado do time;
  • Refatoração dentre outras vantagens óbvias, mantém o código mais simples e tende a reduzir as partes do sistema que apenas uma pessoa entende.
  • Retrospectiva ajuda as pessoas que fazem um projeto a se tornarem um time, expondo problemas e criando um tom mais produtivo que visa buscar solução em vez de culpados.
Vale lembrar que não pregamos o uso de todas essas práticas em 100% do tempo, mas é fundamental que o time conheça e entenda quais vantagens cada uma das práticas promove -- e usá-las de acordo.

Gestão visual

Concordamos com a proposta de XP de manter uma área de trabalho informativa. Seja com quadros na parede ou com ferramentas eletrônicas, a gestão visual ajuda o grupo de pessoas que trabalha em um projeto a olhar além do próprio umbigo e incentiva a colaboração e a manutenção do time. Ainda é importante notar que não basta existir um quadro na parede ou um Trello ou semelhante. É preciso que todo o time esteja sempre atento à ferramenta. Nesse aspecto, acreditamos que quadros na parede tenham uma vantagem intrínseca: a informação está visível para todos, queiram ou não queiram, enquanto ferramentas eletrônicas exigem que o time as acesse e não estão visíveis para o resto dos que passam pelo ambiente do time. Vale medir qual faz sentido no seu caso.

Open Source

A grande maioria das soluções que usamos é open source. Acreditamos na qualidade dos projetos de software livre exatamente porque, ao encontrar um erro, qualquer desenvolvedor pode colaborar enviando patches -- ou, mais recentemente, pull requests. Além disso, acreditamos em devolver para a comunidade, produzindo nossos próprios projetos open source. É claro que há uma tentativa de devolver para a comunidade o que ganhamos dela, mas produzir software livre não é só um gesto altruista! O aprendizado envolvido na produção de um software livre é interessante para a visibilidade da empresa e também para o crescimento individual dos desenvolvedores. Projetos open source são uma excelente forma de colaborar para o crescimento da base de conhecimento mundial e expor sua marca. Use e faça!

Ferramentas

Editor de texto para programar

IDEs trazem muitas facilidades para o desenvolvedor, como refatoração, code completion, navegação no código, etc. Não importa qual seja a sua IDE favorita (Eclipse, NetBeans, Visual Studio), mas use uma. Não somos a favor do uso de editores de texto simples como IDE. Programar usando um bloco de notas não é produtivo e totalmente sujeito a erros. Vale notar que consideramos que editores mais espertos, como VIM, Emacs e Sublime, adicionados de conjuntos de plugins, tornam-se IDEs bastante interessantes para quem sabe usá-las.

Geradores de site estático

Criar e manter um site de conteúdo estático, desde um blog à documentação de um software, não deveriam ser tarefas trabalhosas. A ideia de geradores como o Jekyll é garantir que não sejam. O que diferencia o Jekyll de seus concorrentes e poderia torná-lo uma escolha promissora é o suporte nativo e gratuito dado pelo Github em seu serviço de publicação de páginas, o Github Pages. Porém, certa instabilidade desse serviço pode causar problemas, já que as atualizações do Jekyll são frequentes e não há nenhum tipo de controle de versão. Se você precisa dessa estabilidade e algumas configurações antes do deploy não forem problema, o Jekyll perde seu posto. Existem alternativas mais poderosas para a geração de sites estáticos, como o DocPad, que permite, por exemplo, escolher a linguagem de template utilizada e criar filtros baseados em metadados customizados, features que o Jekyll não oferece.

Controladores de versão

Controladores de versão são populares há muito tempo. Mas, dado que existem diversos, temos hoje algumas preferências. Controladores que fazem uso de travas, como é o caso do Visual Source Safe, devem ser evitados. Já Git e Mercurial são opções bastante interessantes. Ainda mais porque ambos apresentam ferramentas ao redor, como é o caso do Github e Bitbucket, que facilitam bastante a interação entre os vários desenvolvedores do projeto. Apesar de bons, ambos são ferramentas um pouco mais complicadas do que SVN/CVS. Nosso conselho é que, após escolher uma das ferramentas, estude-a para que você consiga extrair o melhor possível dela.

Gerenciamento de dependências

Foi-se o tempo em que era necessário garimpar a internet para achar o link para o download da biblioteca que vamos usar na nossa aplicação. Hoje em dia qualquer ambiente de programação respeitável possui alguma ferramenta em que podemos declarar quais são as bibliotecas necessárias para que a aplicação rode. Esse tipo de ferramenta baixa todas as bibliotecas declaradas, junto com as suas dependências. Portanto, considere fortemente usar o gerenciador de dependências mais usado ou o mais fácil de usar do seu ambiente de desenvolvimento. Dessa forma, com algumas poucas linhas de configuração e um comando conseguimos baixar todas as bibliotecas e suas dependências. Exemplos são o Maven e o Ivy para Java, o Gradle para Java/Groovy, o SBT para Scala, Bundler para Ruby. Em casos raros, caso a ferramenta comece a atrapalhar, por exemplo demorando demais para fazer os downloads ou complicando a configuração, você sempre pode pedir para baixar todas as bibliotecas, incluí-las no projeto e parar de usar a ferramenta.

Server-side JS

O uso de JavaScript no servidor é uma tendência em alta. O grande apelo da linguagem única tanto no servidor quanto no HTML é o maior argumento, diminuindo curva de aprendizado e trazendo mais foco. O Node.JS é a ferramenta mais lembrada pra isso, mas não é simples. Há toda uma complexidade em seu modelo de desenvolvimento assíncrono e muitas limitações quando comparamos a soluções já estabelecidas em outras plataformas. Por outro lado, é uma plataforma com grande potencial de escalabilidade. Recomendamos cautela em sua adoção e, principalmente, uma boa análise do projeto pra ver se o Node.JS é a melhor solução.

NginX

O NginX é uma ferramenta muito estável quando há a necessidade de load balancers ou proxies. Além disso, sua capacidade de servir arquivos estáticos de maneira muito rápido e facilitar diferentes configurações, como quantidade máxima de acessos por um mesmo IP (e assim evitar ataques DDoS) é motivo de nota. Por ser de fácil configuração, recomendamos fortemente a sua utilização.

Profiling

Ferramentas de profiling devem ser utilizadas durante todo o ciclo de desenvolvimento e não apenas quando acontece algum problema no sistema em produção. Reagir é sempre mais complicado do que prevenir. Então sugerimos que as empresas façam analise dos dados constatemente para que possam tentar se antecipar aos problemas.

Linguagens e Frameworks

Component-based frameworks

Apesar das facilidades que frameworks component-based frameworks trazem para o desenvolvedor, escolher um entre os vários existentes é um desafio. As primeiras versões do JSF apresentam tantos problemas e complicações que os benefícios acabam sendo ofuscados pelos problemas do framework. A falta de escopos para manter estado entre as requisições obriga praticamente o sistema inteiro a ser feito com objetos SessionScoped, que aliada a uma estratégia inefetiva de armazenamento da árvore de componentes no servidor causa uma sobrecarga enorme na memória, reduzindo em muito a escalabilidade dos sistemas. Apesar de existirem diversas bibliotecas de componentes, desenvolver um componente do zero é uma tarefa extremamente complexa, o que leva a vários sistemas misturando JSF, html e javascript puros, tornando a manutenção muito mais custosa. Atualmente, com as recentes evoluções da plataforma JavaEE, o JSF a partir de sua versão 2.0 incorporou várias soluções e funcionalidades existentes em projetos como o JBoss Seam, tornando se uma opção viável e competitiva para aplicações web onde se espera uma grande interatividade com o usuário aliada a um desenvolvimento e manutenção simplificados. Com a extensa gama de bibliotecas de componentes ricos como PrimeFaces e RichFaces é cada vez mais fácil encontrar componentes prontos para solucionar seu problema, e com a adição dos Custom Components na versão 2.0 mesmo desenvolver componentes customizados não é mais uma coisa do outro mundo. Na versão 2.2 a evolução continua, com mais componentes default, uma integração melhor com o CDI e com HTML5 e melhorias no desempenho das aplicações de modo geral. O mesmo não acontece com GWT. Ele surgiu como uma ótima alternativa pra desenvolvedores Java que possuiam habilidades em desenvolvimento desktop e muito pouco conhecimento em web. Mas caso sua equipe já possua conhecimentos intermediários em html, css e javascript, o uso do GWT será mais uma barreira do que um auxílio, já que não há controle nenhum sobre o resultado final da página, levando várias vezes à códigos que misturam porções geradas pelo GWT com partes customizadas de HTML e Javascript, além de dificultar a customização visual com css. A opinião é parecida com WebForms, onde o desenvolvedor tinha pouco controle sobre o HTML produzido. Com o advento do Asp.Net MVC e a imensa quantidade de componentes Javascript, é preciso um bom motivo para optar pela solução mais antiga.

Action-based frameworks

Existem diversos frameworks MVC maduros e prontos para serem utilizados dentro de grandes projetos, como exemplo podemos citar: ASP.NET MVC, Ruby on Rails, Spring MVC e VRaptor. Todos os frameworks citados possuem um grande número de ferramentas e plug-ins prontos para serem utilizados em ambiente de produção. Além desses frameworks maduros, temos também os que possuem ideias mais inovadoras como é o caso do Play Framework que tenta trazer algumas caracteristicas do Rails para dentro da linguagem Java (ou Scala), além de trazer inovar na camada de visualização fazendo com que as views sejam compiladas para métodos que podemos invocar a partir do controller. Com isso, é possível saber em tempo de compilação se o desenvolvedor está utilizando a View corretamente. Porém o projeto ainda não possui tantas ferramentas quanto outros frameworks, e sua documentação ainda não é clara. Por isso recomendamos apenas testar o framework em projetos menos críticos. Um outro framework que merece ser citado é o Struts. Esse framework já foi muito importante no mundo web do java, porém atualmente já perdeu sua força e, em geral, é encontrado apenas em projetos legados. Por isso recomendamos a não utilização em novos projetos, em favor de frameworks mais modernos como o Spring MVC e VRaptor.

Pré-processadores e bibliotecas de CSS

Apesar do LESS/SASS e outros geradores de CSS trazerem ótimos recursos para o desenvolvedor, ele torna mais fácil escrever um código ilegível do que com CSS puro. Precisa realmente testar se a equipe consegue se adaptar com essas ferramentas para não ter que refazer o CSS após algum tempo de projeto. Quanto ao Twitter Bootstrap, se não há a necessidade de um layout exclusivo, ele é uma ótima opção para agilizar o processo de front-end. Mas, para customizá-lo, você terá tanto trabalho que vale a pena começar um CSS do zero do que tentar entender o bootstrap e modificá-lo.

Mapeamento Objeto-Relacional

Utilizar frameworks ORM é quase sempre a melhor opção. Eles facilitam e muito o trabalho do desenvolvedor, tirando todo o problema de fazer o mapeamento entre o banco de dados e suas classes/objetos. Necessita-se de um ótimo motivo para que a equipe opte por não fazer uso de um deles. O Entity Framework, o ORM oficial da Microsoft, por exemplo, faz com que lidar com um banco de dados seja igual a lidar com uma simples coleção de elementos. Com isso, o desenvolvedor fazer queries utilizando o LINQ e gravar novas entidades simplesmente adicionando-as à coleção. Porém, por ser um framework novo, ainda não possui uma boa integração com alguns bancos de dados do mercado. Além disso, ainda não possue muitas opções de customização. Por esse motivo, consideramos que o Entity Framework pode ser utilizado em projetos pequenos que utilizam o SQL Server. Quando precisamos de um ORM mais robusto, uma das opções mais recomendadas é o (N)Hibernate, um framework com muitos anos de desenvolvimento e também com muitos usuários ativos. Por ser um framework mais maduro, é possível utilizá-lo com os principais bancos de dados do mercado, além de possuir diversas opções tanto para escrever buscas quanto para fazer o mapeamento dos objetos no banco de dados.

Linguagens que merecem menção

Algumas linguagens devem ser comentadas, pois estão fazendo algum sucesso na comunidade. Scala é um bom exemplo. Acreditamos hoje que Scala pode ser usado para pequenas partes (ou micro-serviços) do seu projeto. Apesar de poderosa, o compilador ainda é bastante lento, e se o desenvolvedor abuse de recursos como mixins, o código pode acabar se tornando complicado e difícil de manter.

Geradores de JS

Apesar de CoffeeScript ter algumas ideias interessantes, a abstração ainda apresenta problemas, que na prática dificultam a vida do desenvolvedor. Um bom exemplo é o debug: as mensagens, bem como a linha que aponta o erro, são difíceis de serem interpretadas. Nesse momento, nossa sugestão é para que você faça uso de Javascript puro, encapsule bem seu código, e faça uso de bibliotecas que facilite o trabalho.

NoSQL

Os bancos de dados não relacionais possuem diversos casos de uso em que funcionam melhores do que a tradicional abordagem relacional. No entanto, tanto os desenvolvedores como os administradores de dados precisam deixar de lado boa parte de seu conhecimento prévio do paradigma relacional e se abrirem para um mundo novo, com abordagens muito diferentes das que estão acostumados. Essa mentalidade é um dos pontos principais para uma adoção de sucesso dos bancos de dados não relacionais. Entender que alguns tipos de bancos de dados são melhores aplicados a determinados problemas pode fazer a diferença para um caso de sucesso da adoção de NoSQL em um projeto.

Plataformas

JavaEE 7

Utilizar as implementações do JAVAEE já é uma realidade. A plataforma chegou em um nível de maturidade muito grande e, aliado a isso, conseguiu atingir um índice de simplicidade enorme. Desenvolver usando EJB's, Mensagens e Transações gerenciadas pelo container está muito fácil. Os servidores fizeram um ótimo trabalho para diminuir o tempo de startup e com isso os argumentos de que eles eram pesados e tudo mais foram jogados para o lado. Para completar, a especificação de Injeção de Dependências uniu tudo isso e veio ainda melhor na versão 7.

SAAS

Temos feito muito uso de software como serviço. Na maioria dos casos, eles barateiam a solução e funcionam bem. Exemplos disso são o Github (nossos códigos-fonte estão hospedados lá), Wordpress (serviço de blog), Iron IO (filas assíncronas), Amazon AWS, e etc. Nossa sugestão é que, caso o serviço necessitado não seja o negócio principal de sua empresa, talvez valha a pena fazer uso de um terceiro, cujo foco é justamente aquele determinado serviço.

Computação na nuvem

Fazer uso de computação na nuvem é com certeza uma escolha acertada. As diversas plataformas existentes no mercado são bem maduras. O GAE, por exemplo, oferece uma administração simples, é fácil de escalar e tem diferenciais como seu armazenamento de dados distribuído que cresce conforme os seus dados aumentam. O Heroku conquista com a agilidade de fazer um deploy, seu ambiente de homologação e variedade de add-ons para incrementar serviços na plataforma. A AWS te fornece uma plataforma elástica de fácil escalabilidade, bastante flexibilidade pra evoluir com de acordo com suas novas necessidades e a evolução da sua empresa, além de uma gigante infraesturura e variedade de serviços. Apesar também de ainda termos feito pouco uso, JElastic também é uma alternativa a ser considerada. Nossa única ressalva atual ainda é com o OpenShift, pois acreditamos ainda que não é maduro o suficiente, comparado aos citados anteriormente.

Mobile

Hoje, o mercado está dividido entre Android (maior penetração) e iOS (maior geração de receita). O Windows Phone aparece como uma terceira opção, mas cremos que vá tomar o lugar de nenhum dos principais -pelo menos não tão cedo. A questão é que usuários de Android ou iOS são fiéis a suas plataformas e, normalmente, investiram dinheiro em Apps. Para que eles mudem de plataforma (e percam parte desse investimento no processo), normalmente precisa acontecer algo grave (seguidas versões ruins, experiências desastrosas, etc.) ou um distanciamento tecnológico muito grande (uma plataforma ficar muito a frente da outra). Vemos muitos usuários de iOS com disposição para tentar Android e vice-versa, mas poucos querendo dar uma chance ao Windows Phone. O Monotouch agora se chama Xamarin (nome da empresa que desenvolve) e é uma alternativa que está ganhando espaço, inclusive chamando nossa atenção. A ideia é escrever uma base de código única, compilar para cada plataforma (iOS e Android, das mobile) e gerar Apps nativos para cada uma. Como conseguir isso, se as APIs são tão diferentes? Usando o .NET Framework (port) ao máximo, deixando pouca coisa para as APIs nativas. Ainda não é 100% mágico, ainda é preciso tratar diferenças entre cada plataforma. Mas está chegando perto! A linguagem usada é o C#, que dispensa apresentações. O IDE está em constante evolução e agora consegue desenhar a interface gráfica de forma integrada (antes era preciso usar o Interface Builder no iOS ou escrever código no Android). Em nossa opinião, a principal vantagem está em usar o C# e .NET framework, possibilitando uma base de código única (ou quase) compartilhada entre Android, iOS e Windows Phone. Está cada vez mais maduro e tem cases muito bons (como o App do rdio, que é excelente e totalmente feito na plataforma).