Arquivo da categoria: Desenvolvimento

Índice de dor de cabeça em projetos de software

Um novo projeto de software é iniciado. Os gestores do projeto começam os rituais de levantamento de requisitos, modelagem e estimativas de custos e prazos. O foco é colocar esse software no ar, sua concepção é o projeto, é o objeto do contrato, é o que está sendo vendido e que vai ser listado em sua lista de conquistas em sua página do LinkedIn.

Mas a experiência na área de tecnologia nos mostra que o que vem depois é que mede de verdade o sucesso desse projeto. Manutenção é uma palavra que não inspira desenvolvedores, ninguém tatua essa palavra no próprio corpo, ninguém faz filmes de ficção científica sobre o tema, mas é uma das principais razões para existirem engenheiros de software profissionais.

Escrever código que funciona é fácil. É algo que qualquer um consegue fazer, basta paciência para aprender usando tutoriais, livros ou professores. Mas o profissional precisa sempre levar em consideração que amanhã alguém vai precisar alterar esse código e algum usuário pode ter um prejuízo se algo não estiver funcionando corretamente. Fazer funcionar é fácil, é a parte do trabalho que é uma ciência exata. Construir algo que é possível de manter funcionando é mais próximo de uma arte, um misto de experiência, intuição e criatividade.

Pensar nos custos de manutenção se torna ainda mais crítico quando você não tem uma equipe grande de desenvolvedores. A maioria das tarefas de manutenção não são possíveis de prever e quanto menos braços a disposição, menor o número de coisas que podem ser feitas em paralelo. Trabalhando sozinho, pode ser que você precise assistir sua cozinha pegando fogo enquanto você tenta apagar o incêndio no seu quarto.

Esses eventos não previstos que geram a necessidade de alteração do código de seu software é o que chamo de “dores de cabeça”. Quando uma dor de cabeça surge, as tarefas que você havia planejado precisam ser adiadas, talvez você precise trabalhar em finais de semana e madrugadas e em alguns casos até cancelar compromissos. Elas existem em todos os projetos, mas existem características que tornam um projeto mais suscetível a alguns tipos de dor de cabeça.

Am13D

Batman, cancele as férias que deu ruim aqui!

Para tentar entender melhor a quantidade de trabalho que podemos ter com a manutenção de um software no futuro, nós precisamos de um índice de dor de cabeça. Com esse índice, podemos analisar pelas características de nosso projeto, quais tipos de dor de cabeça vão afetar nossas noites de insônia. E é claro que isso não pode ser algo exato, com uma fórmula que vai cuspir um número que você pode usar em uma planilha de custos, mas ele pode te ajudar a decidir quais tipos de problema você está disposto a encarar baseado nas decisões de projeto hoje.

Mais funcionalidades = mais dor de cabeça

Este é o fator básico e mais óbvio deste índice. Quanto mais coisas seu software faz, maiores as chances de algo precisar de manutenção.

Seu software vai ter funcionalidades fechadas, como por exemplo funções que calculam algo sem nenhuma interação com atores externos e que portanto são fáceis de testar. Essas provavelmente não vão gerar muita dor de cabeça, a não ser por bug que ocorrem em casos que não foram pensados durante os testes.

Quando você tem funcionalidades em que partes de seu sistema dependem de outras partes do seu sistema, a chance de existirem esses casos de exceção que não foram pensados começa a aumentar. Uma dessas partes pode ser alterada e a interação entre as duas mudar de forma que novos bugs surjam.

Por isso, quando um usuário te pede para implementar algo que parece ser muito fácil, você sempre precisa se lembrar que isso pode virar uma bola de neve de dor de cabeça.

Cada funcionalidade de seu software deve aumentar 1 ponto em seu índice de dor de cabeça.

Bibliotecas e dependências

Uma das vantagens do ofício de desenvolvedor de software é que você pode reutilizar o trabalho de outros desenvolvedores. A cada novo projeto não precisamos criar do zero os sistemas operacionais, bancos de dados, bibliotecas e outros sistemas utilizados em nossa solução.

O problema é que você não tem controle sobre essas dependências por serem mantidas por outras empresas ou desenvolvedores de open source. E isso significa que a manutenção dessas partes do sistema mudam sem seu controle e podem gerar bugs em seu sistema. E é por isso que precisamos ter cuidado ao atualizar nossas dependências.

O que nos impede de usar para sempre as mesmas versões de bibliotecas que sabemos que funcionam? O motivo mais forte é que muitas vezes essas dependências são atualizadas porque uma brecha de segurança foi descoberta. E o outro motivo é que nossas dependências tem suas próprias dependências que podem afetar outras dependências de seu software quando você for forçado a atualizá-las.

Esses dois motivos nos forçam a acompanhar as versões atuais das dependências para manter nossas bibliotecas em versões próximas às versões mais atuais. Atualizar de uma versão para a seguinte já é complicado, mas quando você descobre que precisa fazer o upgrade de algo que está na versão 2 em seu sistema para a versão 10.0 na versão mais atual, comece a rezar.

Cada dependência de seu software deve aumentar em 2 pontos seu índice de dor de cabeça. Cada ponto de versão em que você está defasado em relação à versão mais atual de uma dependência, multiplique esses pontos por 5.

Integrações com outros sistemas

Assim como bibliotecas, integrar com outros sistemas nos poupa de ter que construir tudo que precisamos para que um sistema funcione. E assim como bibliotecas, APIs externas afetam nossos sistemas quando sofrem alterações ou apresentam algum problema.

A diferença é que nós podemos segurar um pouco atualizações de bibliotecas e continuar com as versões que estão funcionando até termos tempo para trabalhar nisso. Já mudanças em APIs têm um prazo para acontecer, e talvez você não tenha a opção de esperar. Ou não receba os avisos de que a API vai mudar. Ou simplesmente esteve tão ocupado que acabe esquecendo e só sendo lembrado quando algo no seu sistema para de funcionar.

Em alguns casos você precisa lidar com mudanças de comportamento de uma API que não aconteciam quando a integração foi feita. Pode ter sido alguma mudança que os desenvolvedores da API acharam que não iam causar muito impacto ou simplesmente alguns erros que você nunca havia visto começam a acontecer porque o sistema da API tem novos bugs ou não está escalando para a carga atual.

E ainda existe o maior problema que são APIs desativadas. Empresas desistem de projetos ou vão à falência e você vai ter que correr para pesquisar, testar alternativas e talvez tenha que construir as mesmas funcionalidades do zero.

Cada ponto diferente de seu código que faz uma chamada para uma API externa deve aumentar 50 pontos em seu índice de dor de cabeça. (Largue a planilha, eu disse que esses números não significam nada).

Legislação

Mudanças em leis podem afetar seu software. Podem ser exigências de como ele deve se comportar, (exemplo: leis de proteção à privacidade na internet). Ou podem afetar os dados utilizados, que vão desde a forma como impostos são calculados até a modelagem de dados (imagine se você tiver tabelas de cônjuges e de repente a poligamia é liberada por lei em seu país).

Essas mudanças nem sempre oferecem um prazo razoável, já que os legisladores não tem como prioridade estimar o quanto cada lei pode afetar sistemas que dependem dessa lei.

Para cada ponto em seu código em que existe um cálculo baseado em lei, adicione 100 pontos ao seu índice de dor de cabeça. Se seu software é usado em alguma área em que a legislação muda muito, adicione mais um número bem grande. Multiplique esse número grande pelo número de páginas da legislação.

O objetivo do índice não é que você procure pela dor de cabeça zero. Um sistema com índice zero com certeza é simples demais e não muito útil. A análise pelo índice serve apenas para que possamos entender os trade-offs que as decisões tomadas na concepção do software podem ter no decorrer de sua vida.

Além disso, a dor de cabeça de uma pessoa pode ser a oportunidade de outra. Você pode oferecer uma solução para algo que os outros consideram uma dor de cabeça. Ou simplesmente oferecer a terceirização da dor de cabeça, para que os outros possam se focar em questões mais centrais a seus negócios.

Camadas de bolo e apps mobile usando javascript e Titanium Appcelerator

Um aviso para que você não perca seu tempo: isto não é um tutorial de Appcelerator, apenas reflexões sobre este tipo de ferramenta baseadas em minha experiência com Titanium Appcelerator. Talvez te ajude a decidir o que usar para desenvolver apps para smartphones e tablets. Ou talvez só te deixe com um pouco de fome, dependendo do horário.

A área de tecnologia se move em saltos muito maiores que outras áreas porque nós usamos muito bem o poder da abstração. Quando uma tarefa é muito complicada de se fazer conseguimos criar uma interface mais simples para essa tarefa, escondendo toda a complicação. Com a complicação escondida em um nível de abstração, essa tarefa pode ser usada como componente de outras tarefas sem que seja necessário pensar muito em seus detalhes.

Isso pode ser observado no desenvolvimento de software com Java, por exemplo. O código Java é um nível de abstração e vai ser compilado para bytecode. O bytecode vai ser rodado por uma máquina virtual que foi escrita e C/C++ e é outro nível de abstração. E o computador executa essa máquina virtual como linguagem de máquina, outro nível de abstração. Esse exemplo poderia ser dividido em vários outros níveis, mas a ideia está aí: cada nível de abstração esconde detalhes para tornar o trabalho de outro nível mais fácil.

Essa é a teoria. Mas muitas vezes um desses níveis de abstração pode não tornar o trabalho mais fácil, ainda mais porque “fácil” é um conceito subjetivo e que depende de contexto. E cada nível aumenta a probabilidade de algo dar errado, porque um erro em um nível mais baixo de abstração vai se propagar para os níveis mais altos. Por isso o valor de usar níveis de abstração não vai necessariamente aumentando a cada nível e por isso não tentamos criar deliberadamente milhões ou infinitos níveis para que o trabalho se torne infinitamente mais fácil.

Eu penso nisso como um bolo com várias coberturas. Na teoria um nível de cobertura deveria tornar o bolo mais gostoso, mais fácil de engolir, mais agradável visualmente. Mas às vezes alguém vai colocar uma camada de chocolate amargo com cacos de vidro e eu não gosto muito de chocolate amargo.

bolo

hmmmmmmmmmmm

Alguns anos atrás estávamos precisando desenvolver apps para iPhone e Android para o Arivo. Como não conheço muito de desenvolvimento para iOS e Android, procurei por soluções que nos ajudassem a acelerar isso, já que precisava ficar mais focado na aplicação web que é a parte principal do Arivo.

Contratar uma agência era uma possibilidade. É um pouco caro demais para o que precisávamos, mas o motivo para não termos escolhido esse caminho não foi financeiro. Nossa aplicação ainda estava mudando muito, o que ia gerar muitas mudanças nas apps e era importante ter mais flexibilidade do que teríamos se contratássemos terceiros para isso. É claro que uma agência iria atender as mudanças no meio do caminho, mas isso ia custar tempo, dinheiro e stress.

Por isso procurei por ferramentas que tornassem esse desenvolvimento mais fácil, ou seja, procurei por algo que me desse um nível de abstração. Além do problema de não conhecer as plataformas iOS e Android, desenvolver para duas plataformas diferentes tomaria muito tempo e esforço. Precisava de algo que me ajudasse a programar apps para as duas plataformas sem ter o trabalho duas vezes.

Existem várias opções no mercado e os critérios que usei, do mais importante para o menos importante:

  • Gerar apps para iOS e Android.
  • Gerar apps nativas. Muitas dessas ferramentas geram apps em HTML5, que na verdade são páginas HTML imitando alguns controles da plataforma, mas que muitas vezes não funcionam exatamente da mesma forma.
  • Usar alguma linguagem de programação que eu conheça bem.
  • Não ter um custo muito alto.

Pesquisei várias opções, como Sencha, RubyMotion, Xamarin, PhoneGap e acabei escolhendo o Titanium Appcelerator. O Appcelerator gera aplicações nativas e usa javascript como linguagem de programação. Pode ser usado gratuitamente mas também tem opções pagas com mais serviços.

No começo, usar o Appcelerator parece um sonho. Criar apps usando javascript ao invés de Objective C e Java sem precisar aprender duas APIs. Rodar as apps nos simuladores, ou em smartphones de verdade, ou gerar os arquivos para envio para a App Store só apertando um botão na IDE. Conseguir desenvolver funcionalidades muito rápido. É a parte doce dessa camada do bolo.

Mas não demora muito para encontrar os cacos de vidro nessa camada.

O primeiro problema é mais uma consequência de gerar apps nativas do que algo causado pela ferramenta. As duas plataformas, iOS e Android tem diferenças de como se comportam e de padrões de interface. Por isso, em alguns casos você tem elementos que se espera aparecerem em uma posição e com um visual que é diferente entre as duas plataformas. O Appcelerator não consegue cuidar automaticamente de todos os casos, então muitas vezes eu preciso enfiar um condicional, um “if (system == ‘android’)” para acertar o resultado final. Poderia uniformizar e ter menos trabalho, mas achava importante respeitar o padrão.

Com o passar do tempo e ao tentar utilizar novas versões é que você começa a encontrar os cacos de vidro maiores e que descem rasgando sua garganta por dentro. Algumas coisas funcionam diferente de uma versão para outra, sem nenhuma documentação sobre essa mudança de comportamento. Você começa a encontrar bugs que foram reportados no fórum do produto e que não foram resolvidos por muitos anos. E você precisa dar um jeito das apps continuarem funcionando para seus clientes, o que significa muita tentativa e erro até conseguir adivinhar como dar uma volta nesses problemas.

Também existem alguns problemas de performance, mas são menores do que esperava de algo que roda javascript. Em celulares de modelos mais antigos a app fica muito lenta a ponto de se tornar um problema de usabilidade. Mas nos atuais funcionam muito bem.

O que é uma pena porque é um produto com muito potencial, e provavelmente se a empresa investisse em qualidade conseguiria resolver todos os problemas. Agora que a Appcelerator foi comparada pela Axway, talvez isso mude, mas eu não vou ficar esperando. No Arivo planejamos criar uma nova versão das apps, provavelmente com uma camada a menos de abstração, mesmo que isso acabe duplicando o trabalho, porque provavelmente muitos dos problemas do Titanium vão ser encontrados nos concorrentes.

Isso é agravado pelo fato de que as próprias plataformas mudam bastante. A cada versão de iOS e Android surgem mudanças e esse tipo de ferramenta que cria um nível a mais de abstração leva um tempo para se adequar e alcançar essas mudanças, ou simplesmente não implementam algumas delas.

No fim diria que não foi um erro usar Titanium Appcelerator, porque ele realmente ajudou com o objetivo de poupar trabalho e lançar rapidamente apps para o Arivo. Mas não recomendaria o uso de uma ferramenta como essa a não ser que a app seja realmente bem simples ou se como nós você tiver a opção de refazer tudo do zero no futuro.

Vale a pena fazer o curso de machine learning do Coursera?

As plataformas de cursos online surgiram nos últimos anos para realizar o sonho de muita gente: poder assistir aulas formuladas pelas melhores universidades do mundo sem precisar sair de casa, enquanto come um Doritos e veste apenas uma cueca. Esse não era meu sonho, mas resolvi que deveria experimentar esse conteúdo pelo menos pela experiência.

Aprendizado de máquina é um assunto que me interessa, por isso resolvi me matricular neste curso gratuito do Coursera. Já havia estudado o assunto antes por conta própria através de livros e até usado um pouco da teoria na prática. Além de poder aprender mais algumas coisas e solidificar o que já tinha visto, essa foi a chance de conhecer e avaliar um conteúdo didático criado em Stanford. É o equivalente para um amante de café ter a chance de experimentar de graça aquele café que é considerado um dos melhores do mundo, feito com grãos retirados das fezes de um roedor que não lembro o nome.

Antes de saber se você deveria fazer este curso é uma boa ideia ter uma noção do que é aprendizado de máquina. E acho que a melhor forma de motivar alguém a conhecer melhor o assunto, é ter uma noção de suas aplicações práticas. Usando machine learning você pode criar software que reconhece objetos em imagens, detecta fraudes em operações financeiras, dirige um automóvel ou drone, avalia o crédito de pessoas, avalia a probabilidade de um paciente ter uma doença, prevê que um servidor pode sofrer uma falha, e muitas outras coisas que parecem mágica. Mas conhecendo melhor sobre o assunto você vai ver que essa lista que fiz é bem limitada.

Depois de se interessar pelo curso, sua preocupação pode ser em saber se você precisa ser um campeão de olimpíada de matemática para conseguir acompanhar o curso. Este é um assunto que usa muita matemática, mas o curso foi pensado para alunos que pelo menos consigam ler uma fórmula com somatórias, matriz e vetores. Existem até aulas opcionais com álgebra linear básica para ajudar com os conceitos que vão ser usados durante as aulas. E graças ao professor Andrew Ng, as aulas são muito didáticas a ponto de ele fazer todos os passos de cálculos necessários nos exemplos. Em casos em que seria necessário um conhecimento matemático maior, o professor dá uma explicação sobre a intuição do que está sendo feito, mas não é exigido que o aluno saiba resolver uma derivada ou decompor uma matriz, por exemplo. Mas minha opinião é que tendo uma base mais do que básica sobre cálculo e álgebra linear vai tornar o conteúdo muito mais fácil de assimilar e entender, sem deixar que alguns passos nos algoritmos pareçam ter aparecido por mágica.

Saber programar é um pré-requisito. Os projetos a entregar são programas escritos em Matlab ou Octave. Mas não é necessário conhecer uma dessas linguagens, pois algumas das aulas vão te ensinar o necessário para realizar todas as tarefas. Eu mesmo nunca havia usado essas linguagens. Apesar de não ser muito difícil de aprender, muitas vezes perdi muito tempo por detalhes da linguagem que causavam erros nas minhas tarefas. Mas o fato de que você só precisar programar o principal das tarefas, com o código que cuida de preparar os dados e mostrar resultados já pronto, facilitou e economizou muito meu tempo, considerando que é um curso que muita gente vai fazer no tempo livre. E o sistema de envio das tarefas com correção automática funciona muito bem. Você resolve cada passo do exercício, envia para o sistema e ele te diz se você acertou ou não.

Um ponto muito positivo é que todo o conteúdo, por ser ensinado pela mesma pessoa, tenta seguir mais ou menos a mesma notação do começo ao fim. Isso ajuda muito para comparar os algoritmos. Quando você tenta aprender cada uma dessas coisas por fontes diferentes, você acaba vendo notações diferentes que dependem da preferência do autor. É como tentar entender uma história que teve uma parte contada por uma pessoa e o final contada por outra, mas a que contou o final só se refere aos envolvidos por apelidos que você não conhecia.

O melhor do curso para mim são as ferramentas que ele ensina para que você entenda se sua solução de machine learning está funcionando bem, e o que você pode fazer para melhorá-la. É esse o conhecimento que eu esperaria de alguém que fosse usar esses algoritmos na prática.

Vejo poucos pontos negativos, que são pequenos perto das qualidades do curso. Algo que me incomoda um pouco são as questões que aparecem no meio dos videos. Muitas vezes eles nem estão testando se você entendeu a teoria que está sendo ensinada, mas verificando se você está acordado e prestou atenção na notação que o professor acabou de usar. Outra coisa que me fez falta, que se deve mais ao formato, é não ter um material que possa consultar facilmente depois. É impraticável procurar no meio dos videos algo que você não lembra direito onde viu, por isso recomendo anotar principalmente as dicas que são baseadas na experiência do professor Andrew.

Talvez algumas pessoas possam se sentir incomodadas pela falta de formalidade técnica que o assunto é tratado, mas considerando que aprendizado de máquina é uma área em que os métodos funcionam mesmo sem os matemáticos entenderem muito bem, acho que o conteúdo habilita alguém a se tornar um praticante. Um conhecimento mais formal seria necessário apenas para quem deseja se tornar um pesquisador na áreae nesse caso este curso funcione bem como uma introdução geral.

Por tudo isso digo que vale muito a pena fazer o curso de machine learning oferecido pela Universidade de Stanford pelo Coursera. Valeria a pena mesmo se fosse pago, sendo grátis eu tenho a vontade de visitar meus amigos programadores e obrigá-los a assistir essas aulas.

Grails & Groovy: primeiras impressões

A maior certeza que você pode ter, se for seguir carreira como programador, é que você vai usar muitos frameworks e linguagens de programação diferentes. Alguns você vai odiar de coração, mas vai ser obrigado a usar. E quando um colega seu citar o nome dessa ferramenta, você provavelmente reagirá como se sua mãe tivesse sido xingada. Mas também haverá os frameworks e linguagens que você vai odiar menos, e que talvez, por comparação com o que você já usou no passado, você chegue até a gostar.

COBOL: não gostei

COBOL: não gostei

Alguns, como eu, nunca ficam muito satisfeitos e sempre estão a procura da solução perfeita. A resposta à pergunta mais levantada por quem precisa parir um projeto: “o que vamos usar?” Esses sujeitos estão sempre experimentando coisas novas, procurando alguma solução que não tenha os problemas que as outras tinham, e quem sabe um dia encontrar o cálice sagrado das soluções de sistemas. E eu TALVEZ tenha encontrado algo bem próximo disso e que por acaso tem o nome de Grails (se você não entendeu está na hora de entrar num curso de inglês – aí CCAA, olha a oportunidade que vocês perderam de fazer merchandising no blog).

Não vou dar o veredito final porque ainda usei muito pouco Grails, em um projeto pequeno, em que um dos maiores objetivos era aprender Grails e Groovy. Mas para vocês terem uma idéia, o projeto envolvia integração com uma interface Flex (o RIA da Adobe) e usava JMS (o padrão de Mensageria Java). E mesmo assim, escrevi muito pouco código, quase nada de configuração e nenhum SQL (sim, o projeto tem banco de dados). Acho que o fato de eu ter tido pouco trabalho fazendo isto já mostra um pouco o porquê de eu ter achado o framework tão bom.

Grails: o logotipo foi o que menos gostei.

Grails: o logotipo foi o que menos gostei.

Outro motivo para não bater o martelo é que ainda não parei para aprender Ruby on Rails. Está na minha lista de “coisas a fazer (ou não)”, mas da forma como é aclamado pelos rubistas, deve realmente ser muito bom. Bom, se bem que “Crepúsculo” é aclamado por muita gente e eu não estou a fim de ver um filme que mistura Malhação com vampiros emos. Mas o fato de Grails ter sido inspirado em Rails não me permite ignorar sua existência.

Minha experiência com o framework foi curta, mas espero poder usar eventualmente para outras coisas. Por enquanto ainda não usaria para um projeto principal, mas para algo menor não teria dúvidas. Seguem abaixo minhas observações sobre Grails:

  • a linguagem Groovy: não gostava muito de linguagens dinâmicas, mas talvez isto tenha sido por conta do período em que usava PHP. Groovy é uma linguagem muito agradável de usar (pelo menos te garanto que é MUITO mais agradável que Java) e que da mesma forma que Perl, te dá diversas formas de se fazer a mesma coisa. E assim como Ruby, te dá a opção de extender a definição de qualquer classe (como adicionar métodos a uma classe da API padrão por exemplo) e de usar closures (que a grosso modo funciona como os ponteiros para métodos e funções existentes em outras linguagens). Me agrada muito a implementação da linguagem, que te poupa de fazer checagens bobas como verificar se o objeto é nulo, ou concatenação de strings, tornando o código mais legível e mais fácil de escrever.
  • plataforma Java: isto é mais vantajoso para quem já trabalha com Java, mas de certa forma é vantajoso para todos pelo tamanho da comunidade Java. O Grails e o Groovy foram contruídos sobre a plataforma Java. Dessa forma, um código escrito em Java é aceito como código em Groovy, o que pode tornar o aprendizado um pouco mais fácil. Um código escrito em Groovy tem total interoperabilidade com código em Java, permitindo que você tenha um projeto com partes escritas em uma linguagem e partes escritas na outra. Tanto que você pode utilizar qualquer coisa que você já podia utilizar em Java (bibliotecas, frameworks, etc). Isso foi aproveitado pelos idealizadores de Grails, pois o framework tem como seus alicerces dois frameworks Java muito populares: Spring e Hibernate.
  • GORM: é o responsável por mapear seus objetos para os registros no banco de dados (daí a sigla ORM – Object-Relational Mapping), e utiliza o Hibernate por baixo do capô. Este é o melhor ORM que já vi, pois de fato torna o trabalho muito mais fácil. Como eu disse, não escrevi uma linha de SQL e também não encostei em nenhum XML de configuração para fazer o GORM funcionar. Utilizar o GORM é basicamente como eu gostaria que fosse utilizar um banco de dados orientado a objetos. Se GORM fosse uma mulher eu casava. Ah, mulher gostosa, claro.
  • plugins: Grails tem uma boa variedade de plugins para extender sua funcionalidade. O que mais me impressionou é a facilidade de se instalar um plugin em um projeto. É tão fácil quanto instalar algo usando apt-get, basta um comando (traduzindo para quem só usa Windows: é fácil pra caralho!). Em um projeto não Grails, normalmente acrescentar uma tecnologia nova, como funcionalidade de web-services ou um motor de busca, sempre gera um certo stress, a ponto de gerentes com mais experiência alocarem um bom tempo na agenda do projeto para a tecnologia ser incorporada sem problemas. Em Grails, você instala o plugin e usa o resto do tempo que seu gerente alocou para ficar pedindo convite para o novo Orkut! SE não fizerem um plugin para isso.
  • ambientes: o framework já vem preparado para rodar sua aplicação nos ambientes de teste, desenvolvimento ou produção, facilitando a configuração para essa divisão por estágios. E não só isso, quando você faz o download do Grails ele já vem com um banco de dados (HSQLDB) e servidor web (Jetty) para que você possa sair escrevendo código sem se preocupar em montar o ambiente na sua máquina.
  • testes: a parte de testes automatizados (tanto unitários quanto funcionais) faz parte do framework, o que faz com que ele reforce o uso dessas boas práticas.

Se você se interessou em aprender mais, a InfoQ tem um livro gratuito (gratuito de verdade) chamado Getting Started with Grails. Para mais conteúdo, eu recomendo um livro não-gratuito chamado Beginning Groovy and Grails: From Novice to Professional. E para trocar experiências, já existe um fórum de Grails e Groovy brasileiro: o Grails Brasil.

Todo mundo odeia pair programming

Pair programming (ou programação pareada) é provavelmente a prática mais polêmica de extreme programming. É um dos poucos elementos de XP que tem seu valor questionado até por muitos desenvolvedores (além de gerentes e clientes). Provavelmente esta seja a razão para pair programming não ser tão praticada, ou utilizada apenas em doses homeopáticas (ainda mais considerando que pode ser utilizada mesmo sem XP ou algum método ágil). Porque existem pessoas em todos os papéis envolvidos no processo, que odeiam pair programming.

Quando um não quer, dois não fazem pair programming

Quando um não quer, dois não fazem pair programming

Muitas dessas pessoas conhecem as supostas vantagens de parear, mas torcem o nariz, mesmo que nunca tenha experimentado ou que tenham feito apenas uma tarde de experiência com o cara mais chato que conhecem no escritório. Mas na minha opinião, essa resistência não é criada por motivos muito nobres. Além do preconceito que já não é algo muito nobre, resolvi analisar algumas concepções erradas que as pessoas envolvidas tem sobre pair programming. Então venha comigo, de cabeça aberta.

Cliente

Se o cliente estiver contratando um serviço de desenvolvimento de sistemas, o problema provavelmente está no contrato. Muitos contratam esse tipo de serviço pagando pela hora dos desenvolvedores. Logo, quando ficam sabendo que em cada estação de trabalho vão trabalhar duas pessoas, já pensam que estão pagando o dobro do que deveriam pagar. Isso se resolve mudando o contrato para alguma outra forma que não envolva contagem de cabeças. Que aliás, sempre achei um jeito muito estranho de se vender este tipo de serviço, como se o número de pessoas (e não a qualidade) fosse determinante para o sucesso de um projeto. Vendendo a hora do desenvolvedor é como se você terceirizasse os riscos do seu RH e ainda lucrasse alguma coisa quando algum cara ruinzinho fosse contratado.

Se o que você está vendendo é justamente a consultoria para melhoria dos processos de desenvolvimento (o que provavelmente envolve pair programming), então você vai ter que vender todos os benefícios dessa prática. Para isto talvez o resto deste post ou outras referências te ajudem.

Gerente

Para o gerente, provavelmente a maior objeção é a questão da produtividade. Se formos cronometrar o tempo que uma dupla leva desde o começo até a entrega de uma tarefa, muito dificilmente os programadores pareados terão mais que o dobro da velocidade de dois programadores sozinhos. O problema de medir a produtividade desse jeito é que ela não leva em consideração a qualidade do que foi produzido e nem a transferência de informação e conhecimento que acontece durante pair programming. De qualquer jeito, medir produtividade desse jeito seria muito simplista. Em engenharia de software, uma gambiarra pode te fazer terminar muito rápido uma tarefa, mas mais para frente a equipe ter uma dor de cabeça de manutenção e gastar muitas horas resolvendo a gambiarra.

Falando em gambiarras, esta é uma das coisas que se pode evitar com pair programming. Com um co-piloto te vigiando, é muito menos provável que o desenvolvedor aposte numa solução rápida mas feia, porque afinal ninguém quer passar imagem de ser desleixado. Por outro lado, ter um co-piloto também evita que o seu super-mega-engenheiro que gosta de comer design patterns no café da manhã crie uma solução super complicada só porque é mais bonita, já que ninguém está olhando (e que depois ninguém vai entender ou vão gastar um tempão desfazendo). Tanto a gambiarra quanto o over-engineering podem custar muito em manutenção nas próximas iterações.

E por último, mas não menos importante, pair programming é a forma mais orgânica de disseminar informações sobre o projeto, compartilhar conhecimento e formar a cultura de um time. É como se você tivesse coaching, treinamento, revisão de código, brainstorm e mini-reuniões o tempo todo, sem precisar parar a codificação. Se você faz rodízio dos pares muito dificilmente precisará se preocupar se seu programador McGyver sumir, porque provavelmente mais de um programador conhece aquele código. Sem falar na disseminação de boas práticas, truques e macetes específicos a bibliotecas e frameworks que só poucos conhecem. Essa dinâmica de trabalho também permite criar um processo de admissão de novos desenvolvedores muito mais realista. Algumas empresas colocam os candidatos para parear com programadores da empresa para sentir se aquele candidato se encaixa na equipe (avaliando tanto o perfil técnico quanto a compatibilidade da personalidade da pessoa com a equipe já existente).

Existem muitos que se empolgam com extreme programming e correm para aplicar, e que na verdade gostam mesmo é da promessa de que não vão precisar produzir pilhas de documentação, passar meses tentando adivinhar como deveria ser o design do sistema. Mas muitos desses caras aplicam XP deixando de fora coisas como pair programming (para não desperdiçar contagem de cabeças). É aí que a qualidade começa a cair, porque as duas principais formas de comunicação na equipe (documentação e pais programming) foram abolidas. Sem comunicação em uma equipe, você sabe o que acontece.

Desenvolvedor

Aqui eu vou assumir que estamos falando de um desenvolvedor que seja honesto e esteja compromissado com a equipe e com a qualidade do projeto. Por isso nem vou falar do carinha que preferia trabalhar sozinho só para poder ter mais tempo ao MSN, Twitter e Orkut e nem do programador que não está nem aí para a qualidade do que produz e só está preocupado em receber o salário e bater ponto. Esses não tem muita razão para gostar de pair programming (talvez não tenham razão nem para estarem empregados).

Mesmo para as pessoas honestas e esforçadas algumas das razões para odiar pair programming não são ditas em voz alta. Uma delas está relacionada ao ego, esta parte tão sensível de tantos programadores. Nisso se encaixam os dois extremos, tanto o cara que não confia muito no próprio taco e fica se perguntando se deveria refatorar tudo o que faz, quanto o programador rock star que tem muita experiência e se imagina capaz de escrever um software que faça seu trabalho. O primeiro vai preferir trabalhar sozinho para não ficar exposto ao julgamento de outra pessoa e o segundo por sentir que não precisa de ajuda e na verdade seu par só vai retardá-lo. Ambos seguem um raciocínio que ignora o fato de que um dos objetivos de pair programming é equilibrar a troca de experiências e de informações. O inexperiente aprende algo e o super experiente ajuda o time a se tornar melhor. Pair programming é um exercício de humildade.

Não quero ninguém me desacelerando no meu trabalho diário de SER FODA!

Não quero ninguém atrapalhando meu trabalho diário de SER FODA!

Provavelmente o fato dos desenvolvedores estarem confortáveis com a forma de trabalho atual seja a maior barreira para adoção de pair programming. Claro, você poder ficar no seu canto e fazer as coisas do seu jeito, no seu tempo é muito agradável. Também acharia super agradável trabalhar na praia, sem computador nenhum e podendo dormir o quanto eu quisesse. A grande questão é o quanto a predominância desse trabalho individual ajuda o trabalho em equipe, principalmente quando falamos de comunicação. Claro que a adoção de trabalhos em pares não significa que as pessoas não possam ter seus momentos de trabalho solitário, que em alguns casos são necessários (coisas que necessitem de muita concentração, como uma leitura por exemplo).

Talvez como complemento você se interesse por ler o excelente post de Obie Fernandez sobre o assunto “10 reasons pair programming is not for the masses” (em inglês), que apesar do nome é uma defesa da prática. Esse post foi escrito logo após o New York Times publicar uma matéria sobre o tema: “For Writing Software, a Buddy System“.

Desenvolvedor de software: esta é a sua era!

Houve um tempo em que você precisava encontrar um poço de petróleo para ficar rico. Em um passado mais recente, você precisava ter as manhas (e os nervos de aço) de Wall Street para isso. Mas hoje, mais do que nunca, estamos vivendo a era do desenvolvedor de software, do programador, do engenheiro!

Provavelmente muitos estão pensando que eu cheirei uma mistura de 7 drogas alucinógenas para escrever isto, porque trabalham na área e, apesar de não ganhar um mau salário estão longe de poderem se declarar milionários ou algo do tipo. Muitos provavelmente acham que poderiam ganhar mais e alguns até migram para outros países para ter um rendimento melhor.

Mas acreditem em mim quando digo: nunca antes esteve tão próxima a possibilidade para uma pessoa esperta, com um computador conectado à internet, de fazer muito dinheiro, de gerar um império e de posar tomando champagne na ilha de Caras.

Pode ser você na próxima capa!

Pode ser você na próxima capa!

Então quais são os fatores que tornam o presente tão especial assim para quem escova bits? Em nenhuma ordem em especial, eis a pequena lista:

  • Software de código aberto e de graça: hoje podemos dizer que software livre é uma realidade madura, não apenas um sonho de programadores barbudos. Tanto que existem empresas que se baseiam em open source e não precisam vender seus rins para continuar funcionando (ou podem ganhar algumas centenas de milhões como no caso da SpringSource). Hoje uma pessoa pode iniciar um negócio sem precisar gastar fortunas com software ( e normalmente desenvolvedores são bons o suficiente para lidar com esse tipo de software). Além disso, como estamos falando de desenvolvedores de software, código aberto pode servir como blocos de construção para partes de seu produto ou serviço, diminuindo radicalmente seus custos de desenvolvimento.
  • Computação em nuvem: esta é uma tendência bastante recente e que ainda está amadurecendo. Graças à computação em nuvem você não precisa ter um CPD só seu, ou comprar uma porrada de servidores que você nem sabe se vai precisar e ainda ficar mantendo. A computação em nuvem permite que alguém tenha à sua disposição uma enorme quantidade de poder computacional a um custo muito baixo,  proporcional à sua necessidade. Se você é um desenvolvedor, esta é a forma mais barata de disponibilizar algum produto/serviço para um grande público e poder aumentar seu poder conforme a demanda aumenta. É uma tecnologia que foi um presente dos céus (ok, esta foi muito infame).
  • Internet e redes sociais: nem a internet, nem as redes sociais são novidade, mas o amadurecimento desse conceito de interconectividade das pessoas amadureceu muito (Twitter e Facebook que o digam). Hoje conhecendo a rede, uma pessoa pode divulgar seu produto/serviço com um custo muito menor e com um alcance muito maior, sem precisar gastar fortunas com uma consultoria de marketing. Hoje você pode lançar serviços para o mundo todo, com clientes que você nunca vai encontrar cara a cara, mesmo que você trabalhe de um pequeno escritório com 10 pessoas (contando com a tia do café). Além disso, hoje você pode aprender qualquer coisa relacionada à tecnologia e programação utilizando a Internet, sem depender de cursos e livros, e de graça.
  • Baixo investimento inicial: os itens acima ajudam muito a diminuir o investimento necessário. Mas se você parar para pensar na idéia de algumas pessoas em uma garagem, com um computador conectado à Internet, deve concordar comigo que existem poucos tipos de negócios que podem ser criados com um investimento tão baixo mas com capacidade de gerar tanto retorno, quanto trabalhar com software. Você não precisa se preocupar com matéria-prima, fornecedores, estação do ano, cotação do dólar (em geral). Tudo vêm da sua cabeça! Pense na poesia disso: você pode construir coisas poderosíssimas a partir do nada! Você é praticamente um deus!

Mas se esses fatores estão aí, são de conhecimento de todos, porque não temos programadores se tornando milionários toda semana (aqui no Brasil pelo menos)? Lembre-se que eu mencionei que o desenvolvedor que tem potencial de tudo isso deve ser um pouco esperto. Na verdade, não só esperto, porque iniciar um negócio, principalmente envolvendo inovação tecnológica, sempre exige uma dose de sorte e perseverança. Se isso não te assusta, o que mais você precisa levar em consideração:

  • Você precisa entender um pouco de negócios: quando digo isso não quero dizer que seja necessário que um cara apaixonado por Lisp precise se tornar o Jack Welch. Mas você precisa começar a considerar o que é mercado, concorrência, receita, fluxo de caixa e principalmente: produto. Comece a estudar casos de sucesso e fracasso que se pareçam com o que você tem em mente. E mantenha foco no mais importante e mais simples: o que eu posso oferecer como produto é algo bom o suficiente para alguém se interessar?
  • Idéias estão por todos os lados: acho que até existe muita gente que tem vontade de começar um negócio, mas a desculpa mais usada é que não tem uma idéia. Acho que quando você começa a dar mais ouvidos para seu chato interior, você começa a ver que falta de idéias não é uma boa desculpa. Sabe aquele produto/serviço/software/sextoy/whatever que tinha algum problema, algum detalhe, alguma coisa que realmente te irritou, e que você queria que fosse diferente? Você pagaria por isso se fosse diferente do jeito que você imaginou? Então está aí, o seu produto. Se mesmo com meu processo de criação você não conseguir pensar em nada, delicie-se com a lista de idéias que o Paul Graham da YCombinator disponibilizou um tempo atrás: http://ycombinator.com/ideas.html
  • Não tente ser perfeito: não sei se é algo que eu posso realmente generalizar, mas acho que na cabeça altamente lógica dos programadores, eles procuram o negócio perfeito, da mesma forma que gostariam de construir software sem bugs. O negócio que vai deixá-los ricos e famosos com o mínimo de trabalho, e vai funcionar de forma perfeita quase como mágica, fazendo o Google se sentir humilhado. Mas isso é perda de tempo. Foque em conseguir fazer algo bom o suficiente. Tentar alcançar o perfeito é simplesmente caro demais. Olhe para as empresas que prosperam, e verá que elas não são perfeitas, nem seus produtos (às vezes, bem longe disso). As melhores são as que focam em fazer algo bom o suficiente.
  • Diminuindo os riscos: você não precisa largar seu emprego para começar um negócio. Vai te custar algum tempo que antes era livre para outras coisas, mas pode ser seu bilhete para um pouco mais de liberdade, em troca de um pouco de stress que o medo do incerto iria te gerar (principalmente se você tem família para sustentar).
  • Obtendo investimento: infelizmente no Brasil não temos tantos casos de investimentos quanto um Vale do Silício, em que você acaba esbarrando com investidores nos restaurantes locais. Mas eles existem. Tente focar no simples: se eu fosse um cara com um bocado de dinheiro para investir e fazer mais dinheiro, eu apostaria no meu negócio? Escreva um plano de negócios e mostre que não investir em você pode ser uma oportunidade desperdiçada.

Eu sei que eu falei muito de dinheiro, mas acho que a regra de ouro é você fazer algo que você vá gostar. Começar um negócio porque você acha que qualquer emprego que te ofereçam ou que você consiga por aí não vai satisfazer seu potencial. Porque se você parar para pensar, tudo que falei dá um trabalho animal, maior do que provavelmente você encara no seu emprego. Se você vai ter muito trabalho, é melhor que seja com algo que você goste (provavelmente se você não gosta, você nem vai aguentar muito tempo tentando). E que a médio ou longo prazo vai te dar alguma satisfação pessoal. Porque o fator mais incerto disso tudo é o retorno financeiro.

E o que vou falar agora vai soar como coisa de livro de auto ajuda, mas é algo em que eu realmente acredito (além do Paul Graham e Guy Kawasaki). Se for fazer algo, faça algo para mudar o mundo para melhor. Sério, soa meio idealista e romântico, mas eu não acho que a promessa de retorno financeiro seja um motivador o suficiente para trilhar esse caminho tão difícil. Quando você faz algo que torna a vida de algumas pessoas melhor, você está mudando o mundo para melhor. Quando você dá o exemplo do que é agir corretamente e com valores, você está tornando o mundo melhor. Você conhece algo mais motivador do que mudar o mundo para melhor?

Faça história!