DSLs não são para gerentes

Já vi e ouvi de muitas pessoas e em muitos lugares que Domain Specific Languages são uma ótima ferramenta para deixar o código tão simples de escrever, tão legível e tão parecido com uma linguagem natural (português, inglês), que serve para que não programadores possam escrever parte do código.

A idéia é que o próprio gerente, cliente, analista-não-programador, ou alguém com este tipo de perfil não técnico escreva as regras de negócio em uma linguagem muito parecida com a linguagem natural, eliminando a necessidade de programadores e reduzindo os custos.

Este pode até ser um uso possível e interessante para DSLs, mas infelizmente, DSLs não tem a mínima pretenção de serem linguagens naturais. Isso seria muito ambicioso para o escopo de uma línguagem específica para um domínio. DSLs não foram criadas para ensinar inglês ou português aos computadores.

Existe uma outra forma interessante de usar DSLs, pela qual tenho preferência declarada e felizmente, parece haver uma convergência para esse meio de aplicá-las. O objetivo é fazer com que o código fonte do programa fique mais próximo do problema sendo resolvido. DSLs como forma de aumentar a expressividade do código. Dave Thomas e Andy Hunt tratam desse assunto no famoso livro The Pragmatic Programmer, sob o nome de Program Close to the Problem Domain.

Em seu livro Domain Driven Design, Eric Evans fala muito sobre a importância de todos os envolvidos no desenvolvimento do sistema usarem a mesma linguagem, que ele chama de linguagem ubíqua (Ubiquitous Language). Desta forma, conseguimos diminuir o abismo que existe entre programadores e especialistas no negócio, facilitando comunicação e diminuindo os clássicos problemas do “telefone sem fio”.

problemas de comunicação

problemas de comunicação

DSLs são uma ferramenta para o desenvolvedor. Uma das formas de inserir os termos da linguagem ubíqua no código fonte, de fazer o código refletir o problema que está sendo resolvido. Desta forma, programadores podem fazer com que o código fique auto explicativo e auto documentado. O próprio código se explica; é a documentação de si próprio.

Ando tão “viciado” nessa forma de escrever código, perseguindo expressividade, fazendo com que o próprio código se explique, que em muitos casos a DSL surge naturalmente depois de algumas refatorações. Aqui, Behavior Driven Development (e principalmente o ciclo red-green-refactor) tem ajudado muito, mas esse assunto fica para um próximo post.

Uma técnica simples para aumentar a expressividade é evitar escrever comentários no meio do código. O tradicional “comentário é mal cheiro no código” (code smell).

Ao invés de escrever o comentário, simplesmente extraia o código que estaria sendo comentado em um novo método. O nome deste novo método deve ser exatamente o mesmo que iria ser escrito no comentário.

“You’ve written the code, now you have to write about the code. In a perfect world, you’d never have to write comments for this purpose: the code will be expressive enough that someone who reads it will understand it. Two things help achieve this result: expressive, readable languages and the composed method pattern.” — Neal Ford

Neal Ford diz que linguagens expressivas e legíveis ajudam a eliminar a necessidade de explicar o código. Geralmente, linguagens mais modernas são mais expressivas do que as mais antigas como Assembly. Mesmo usando linguagens mais modernas, ainda podemos usar nossa ferramenta de programadores preferida: DSLs para criar a linguagem com a expressividade adequada para resolver o problema!

Essa técnica tem o seu preço, claro. É sempre uma troca, uma questão de vantagens e desvantagens; clássico trade-off. Projetar uma DSL pode dar mais trabalho no início, já que precisamos pensar em como desejamos escrever o código (Language Oriented Programming) e pode exigir alguns ciclos extras de refatoração até o código chegar num nível bom de expressividade.

O que tenho percebido é que esse possível esforço extra no desenvolvimento (nem está comprovado cientificamente que ele existe [1]), costuma compensar mais para a frente, dada a facilidade de ler e entender o código, associado ao fato dos programadores estarem naturalmente o tempo todo usando a linguagem ubíqua.

Além disso, diminui bastante a necessidade da famosa pilha de documentação extra que precisa ser escrita em muitos projetos. Na maior parte deles isso tudo é até escrito quando o software já está pronto! Não estou querendo dizer que manuais não devam ser escritos, mas boa parte desse esforço extra de documentação pode ser reduzido. Principalmente o esforço relacionado a documentação que tem como alvo outros desenvolvedores e pessoas que possivelmente darão manutenção no código.

Assim como os testes durante o desenvolvimento, podemos encarar o uso de DSLs como um investimento, e não tempo extra no desenvolvimento.

Feliz ano novo a todos!


1. eu até acho que fico mais produtivo escrevendo código desse jeito.

14 Comentários

  1. Luiz Alberto Hespanha 30/12/2008 at 05:30 #

    Parabéns pelo texto Fábio! Muito bom….

    Um ponto sobre DSLs que eu tenho questionado ultimamente é a curva de aprendizagem de alguém novo entrando em uma equipe. O choque de entrar em uma equipe para dar manutenção em um sistema já é grande, com DSLs eu acho que aumenta ainda mais, já que a pessoa vai ter que aprender além de tudo, uma nova “linguagem”.

    Ainda não sei dizer que o ganho de produtividade da equipe vale tanto a pena pra aumentar ainda mais a curva de aprendizado de alguém novo.

    []’s

  2. Fabio Kung 30/12/2008 at 07:03 #

    Oi Luiz,

    Acho que isso vale muito sim para DSLs externas. Para DSLs internas acredita-se que novos integrantes da equipe tenham que conhecer a linguagem “mãe” (hospedeira).

    A DSL interna nesse caso está aí mais mesmo para deixar o código escrito na linguagem host (Java, C#, Ruby, Python, …) mais legível. Eu considero isso até positivo para a curva de aprendizado e entendimento do código.

    Com relação a uma DSL externa, seu ponto é muito bom. Como isso envolve a criação de uma linguagem totalmente nova, também precisamos considerar a curva de aprendizado dela e tomar cuidado ao misturar muitas dsls externas em um sistema só.

  3. Pedro Cavaléro 30/12/2008 at 15:51 #

    Grande Kung!

    Parabéns pelo post. Quando comentaste sobre este tema no curso de arquitetura, percebi o quanto DSLs internas são interessantes. Às vezes me pergunto o quanto uma DSL interna é parecida com um framework ou até um componente resultante de um processo de negócio. Será que um bom design OO chegaria em uma dsl? ou o contrário?
    Parabéns mais uma vez!
    Abraço!

  4. André Faria Gomes 30/12/2008 at 23:32 #

    Muito bom Kung.
    Recentemente o Martin Fowler fez um post sobre isso em que cita:
    “The sweet spot, however is in making DSLs business-readable rather than business-writeable”. Acho que esse é o caminho.

    Abraço

  5. Rubem Azenha 31/12/2008 at 05:47 #

    O Martim Fowler falou sobre isso também: http://martinfowler.com/bliki/BusinessReadableDSL.html

    “When people talk about DSLs it’s common to raise the question of business people writing code for themselves. I like to apply the COBOL inference to this line of thought. That is that one of the original aims of COBOL was to allow people to write software without programmers, and we know how that worked out. So when any scheme is hatched to write code without programmers, I have to ask what’s special this time that would make it succeed where COBOL (and so many other things) have failed.”

  6. Raphael Brasília 01/01/2009 at 11:52 #

    Iae Dr. Kung!! Fiz o FJ-91 recente aí em sampa contigo!
    Bom, virei teu fã agora!! hehehe! não atualiza teu blog mas mandou seu recado aqui!! auhuhahuaauh!!

    Bom, pelo visto DSL, DDD vieram pra ficar neh? Tava vendo, até o Guru está fazendo um livro sobre… http://martinfowler.com/dslwip/

    PS: Virou mesmo fã da MicroSoft hein? Citando o code smell agora!! auauhhua! Quem diria!! uhauhahuauha!

    Abração feliz ano novo e parabéns mais uma vez pelo trabalho!!

  7. Fabio Kung 02/01/2009 at 00:13 #

    @Andre Faria @Rubem Azenha

    Eu realmente não tinha lido o post do Fowler. Logo depois que postei que abri o Reader e li. Até pensei em atualizar o post para citar, mas como vocês já fizeram isso mesmo. ;-)

    Obrigado pelos comentários. Adorei o post do Fowler. Também acho que é bem por aí mesmo.

    @Raphael

    Não espalha por aí que tem a ver com a MS! hehe

  8. Rodrigo Yoshima 05/01/2009 at 01:44 #

    Uma planilha eletrônica é uma DSL. E os gerentes usam. Pode ser que atualmente não tenhamos o poder que queremos, mas no futuro sim. Eu acredito num futuro sem programadores.

  9. Adenauer Gabriel 17/02/2009 at 11:53 #

    Fala Fabio…
    Parabens pelo ótimo post!
    Depois das discussões que tivemos sobre DSLs no curso, venho colocando isso em pratica nos refactory’s que faço.

    Mas, mesmo deixando a expressão do dominio no código, alguns desenvolvedores pedem para adicionar o velho javadoc… Acredito que é para ve-lo na IDE…rs Enfim isso é cultural!

    []

  10. Felipe Oliveira 17/06/2010 at 12:43 #

    Olá Kung, acredito muito em extrair regras do código, assim como interesses ortogonais também, como policies. O JBoss Seam pode usar o Drools como motor de regras para as políticas de segurança, deixando o código específico fora do contexto da aplicação, muito interessante :-).

    Uma dica para o pessoal que está pensando em escrever DSL´s seria as plataformas BRMs, que são específicas ao problema e facilitam um bocado.

  11. Felipe Oliveira 17/06/2010 at 12:46 #

    E só para citar o que o Yoshima disse sobre planilhas eletrônicas, várias plataformas BRMS possuem plugins para excel, exatamente para as regras serem definidas por uma equipe de negócios.

    Acredito que um software vai precisar de um programador para fazer o warmup inicial, depois disso, acredito também que estamos caminhando no sentido da automação dessas tarefas cotidianas.

  12. Ricardo Herrmann 17/06/2010 at 14:20 #

    No mundo Lisp, bons programadores preferem vê-lo como uma linguagem de programação programável, onde vc usa metaprogramação pra criar uma linguagem mais próxima à estratégia de modelagem e resolução do seu problema. Isso também pode ser visto como uma abordagem de criação (geralmente bottom-up) de uma (e)DSL e a idéia também é aplicável a outras linguagens de programação de propósito geral, mas nem sempre com a mesma elegância, graças à (falta de) sintaxe de Lisp. Em outras linguagens como Ruby e Haskell dá pra encontrar bons exemplos dessa abordagem nas libs por aí, e também um pouco em C++ (boost::spirit é um bom exemplo).

    Just my 2 cents.

Deixe uma resposta