Premature Encapsulation is the Root of All Evil

26 respostas
ViniGodoy

Estava lendo esse artigo:
http://www.adam-bien.com/roller/abien/entry/premature_encapsulation_is_the_root

Ok, o texto é bem exploratório, mas me fez pensar.

Em 12 anos trabalhando profissionalmente na área posso contar nos dedos quantas vezes precisei alterar a base de dados do meu programa. Nessa única vez, mesmo com todos os DAOs, o trabalho se mostrou hercúleo e praticamente inviável. E olha que estava trocando de um banco que suporta o supostamente padrão SQL, por um outro de mesmo tipo.

Por isso, pergunto aos senhores. Algum de vocês já foi realmente beneficiado por usar DAOs? Realmente justifica-se a complexidade adicional inserida no código, os frameworks para gerencia-los, e demais problemas que o aumento da complexidade como um todo geram?

26 Respostas

javaBeats

O real benefício dos DAOs pode ser melhor visualizado quando você tem mais de uma fonte de dados (além do tradicional banco de dados relacional). Imagine recuperando informações sobre seu modelo de mais de uma fonte - você vai perceber os benefícios do DAO e do DomainStore.

Ser capaz de abstrair o acesso aos dados utilizando componentes comuns e reutilizáveis é uma grande vantagem. Sem contar que, aliado a um modelo de entidades bastante coeso e bem modelado, você facilita muito o desenvolvimento das camadas superiores. Eu tenho sempre DAOs “genéricos” disponíveis no código, e eles facilitam muito o desenvolvimento. O que eu NÃO faço é construir DAOs para diferentes entidades sem haver uma necessidade justificável para isso.

Acho que o grande problema com DAOs é que hoje eles estão supervalorizados; serviços com acessos à contextos de persistência costumam substituir código de DAOs com facilidade e presteza.

Rubem_Azenha

Eu uso DAO para não ter código de Hibernate/JPA/ETC espalhado pela aplicação inteira.

prefiro ter um DAO e fazer

findByXPTO

do que

q = em.createQuery("asdadasdasda");
q.setParameter(112321,1231231);
q.setParameter(112321,1231231);
q.setParameter(112321,1231231);
q.setParameter(112321,1231231);
q.getResultList();
Y

Eu concordo com o texto, e acho que isso cai naquela discussao do outro topico sobre daos e repositorios, pq eu preciso a abstracao das camadas dao e etc… se eu tenho uma api simples como jpa ou hibernate pra trabalhar?

No principio eu discordava, achava que precisava de um repositorio e ele delegava para os daos, ai eu tinha as interfaces dao, as implementacoes do hibernate e por ai vai, mas a unica coisa em que isso resultava era trabalho extra. Passei a escrever os metodos de busca diretamente na implementacao do repositorio e pronto. Bem mais simples e nao perco em nada a organizacao.

Agora vale deixar claro pra quem for ler o texto, pra nao confundir o nao encapsulamento prematuro com bagunca. Nao eh porque vc nao precisa de toda uma hierarquia de interfaces e implementacao do pattern dao que voce vai ficar enfiando chamada a api do hibernate/jpa/etc no meio das regras de negocio.

Usei os daos como exemplo, mas isso serve pra qualquer camada adicional que seja feita so por modismo, ou porque alguem “leu em algum lugar”.

Sobre mudar o banco de dados eu ja precisei fazer mais de uma vez, do firebird para o sql server porque o cliente tinha a licenca e nao queria abrir mao e depois passei a usar o postgre como banco padrao. O tempo que levou foi o de criar o esquema no outro banco e alterar a configuracao do hibernate. Claro que isso foi gracas ao hibernate e nao aos daos, mas eh uma coisa que acontece.

FredMP

Olá. Eu ainda tenho pouca experiência nessa área, mas acredito que a criação de camadas de abstração deva ser algo que se justifique de acordo com a necessidade. Pelo que entendi no artigo o cara meio que critica a utilização do padrão DAO por “costume”, sem que se reflita antes sua real necessidade naquele contexto, ainda mais em situações nas quais já temos outras camadas de abstração como a JPA.
Mas mesmo assim eu acho interessante quando possível ter um DAOGenerico que encapsule o máximo da JPA ou JDBC, dependendo do projeto.

Tipo:

DAO dao = new DAO();
Cidade cidade = dao.localizar(Cidade.class, "CidadePorNome", "Cabo Frio");
List<Cliente> clientes = dao.listar(Cliente.class, "ClientesPorCidade", cidade);

E nos bastidores então tratar as chamadas da JPA.

[]'s
Fred

Felagund

Eu acredito na necessidade de daos somente quando existem diversas consultas repetitivas nos códigos, quando se usa um EJB Container, onde cada consulta esta atrelada a um metodo e vc pode injetar os beans em outros beans, não vejo necessidade alguma de usar um DAO. Mas em uma aplicação para evitar diversas consulta repetitivas acredito que DAOs para centralizar as consultas são necessários sim.

[]'s

ViniGodoy

Claro, foi para isso que os DAOs foram feitos. Mas o questionamento é justamente esse. Na absurda maioria das vezes, você não tem mais de uma fonte de dados. Ou não vai mudar o seu acesso. Ou, mesmo com os DAOs, o trabalho vai ser extremamente complexo (escrever vários DAOs também é bastante difícil, especialmente se sua aplicação já passou por otimizações para aquela base de dados).

Bastante vantagem? Mas é uma vantagem para algo que potencialmente você não vai usar?

É, acho que é mais ou menos por aí também. A gente vê muita gente no GUJ partindo para DAOs, VOs e frameworks complexas sem nem sequer se perguntar o porque.

sergiotaborda

Claro, foi para isso que os DAOs foram feitos. Mas o questionamento é justamente esse. Na absurda maioria das vezes, você não tem mais de uma fonte de dados. Ou não vai mudar o seu acesso.

Isso é parcialmente verdade. “Maioria das vezes” … hummm …

No meus sistema é raro quando eu não preciso ter mais do que uma fonte de dados. A razão é simples : testes automáticos.
Não vou acessar o banco real durante os testes, nem me vou dar ao trabalho de ter um banco de testes. Eu não estou testando o acesso ao banco (eu confio no jdbc) e sim as features do sistema. Então é comum utilizar algum tipo de objecto que encapsula o acesso a dados ( não necessáriamente um DAO ou um DomainStore) e posso mudar sem causar problemas no resto da aplicação.

O texto que referiste está equivocado. Ok, é verdade que a maioria das pessoas não sabe construir uma arquitetura e abusa de pseudo-padrões ( cosias que o cara acha que implementa o padrão X, mas não realidade não) Mas quando vc tem que testar o sistema de forma automática o uso de padrões não apenas é correto como é mandatório. O mecanismo de teste ( O Junit) cria um ambiente de execução diferente do habital para a aplicação e isso força configurações diferentes e o “encaixe” de peças diferentes na estrutrua. Trocar um serviço real que conecta ao sistema X por outro que responde um objeto fixo e simula a comunicação , ou substituir o serviço real por um que lança execptions é prática comum. Esta necessidade de agradar a dois clientes/ambientes força um design melhor e o melhor design é automáticamente mais flexivel.

Usar OO corretamente nunca fez mal a ninguem. Esta conversa de que usar padrões de mais é errado é de quem não sabe usar padrões. É desculpa de mau pagador (aluno).

Se vc quer testes automáticos , vc os quer rápidos. E isso passar por trocar a fonte de dados.
Por outro lado, ao fazer teste é prático ter um conjunto de dados que simulam as várias situações dos testes. É dificil ter estes dados e são construidos junto com os testes num processo iterativo. O ponto é que vc precisa ter controle sobre eles. Isso normalmente pode ser feito substituindo a fonte de dados.

Não estou dizendo que é facil. É dificil. E por isso a maioria das pessoas não o faz. E por consequencia não usa testes automáticos. Mas se vc usa testes automáticos vc é inevitável usar um design mais flexivel. Às vezes isso o obriga de não usar alguma framework da moda só para poder ter testes automáticos. É um trade-off importante. Tlv o mais importante ao construir uma aplicação OO.

javaBeats

Uma boa conclusão que podemos tirar dessa discussão é a necessidade de refletir bastante antes de começar a codificar, sobre quais as reais necessidades do seu projeto. E não adotar tecnologias e padrões baseados em o quão legal isso vai se encaixar no seu currículo, ou o quão complexo o sistema PODERÁ ficar no futuro (pseudo-requisitos), etc.

O que acontecia com frequência até pouco tempo atrás é o uso exagerado de “buzzwords” no ciclo de desenvolvimento, em caráter experimental, afim de se familiarizar com uma tecnologia/pattern para conhecimento próprio/da empresa, sem avaliar a real necessidade da aplicação da mesma a longo prazo no projeto. Tenho encontrado esse comportamento cada vez menos em equipes de novos projetos, o que me leva a crer que a comunidade está se conscientizando nesse sentido, e arquitetos malucos estão perdendo espaço para projetos funcionais e ágeis :wink:

Edufa

Concordo parcialmente, é fácil vc ter uma base em mysql e nos testes usar H2 ou HQSQL ou outras similares, onde vc tem total controle e pode testar repetidamente as mesmas situações.

Se não existe nenhum código otimizado especificamente para uma base de dados, apenas mudando o persistence.xml vc resolve esse problema, porém em aplicações mais complexas isso não é suficiente e realmente acaba sendo necessário uma abordagem diferenciada.

De qq forma um código otimizado pode não funcionar na base de testes, por algum tipo de limitação e no final vc pode acabar tendo de ter uma base Mysql tb para testes.

ViniGodoy

O problema que o DAO visa resolver não é trocar a fonte de dados. Mas interoperar entre fontes de diferentes tipos.

Geralmente, quando faço testes unitários, rodo no mesmo tipo de fonte. Isso é, se vou usar SQL server, tenho uma base de testes no próprio SqlServer. Se vou usar MySql, terei uma base de testes no próprio MySql.

Isso evita surpresas também. Quanto mais próximo os testes forem do ambiente real, melhor.

E, para trocar entre fontes de mesmo tipo, o DAO simplesmente não é necessário.

sergiotaborda

ViniGodoy:
O problema que o DAO visa resolver não é trocar a fonte de dados. Mas interoperar entre fontes de diferentes tipos.

Geralmente, quando faço testes unitários, rodo no mesmo tipo de fonte. Isso é, se vou usar SQL server, tenho uma base de testes no próprio SqlServer. Se vou usar MySql, terei uma base de testes no próprio MySql.

Normalmente uso uma implemenação em memoria com Map. Previamente carrega com o dados de teste. A minha fonte de dados não é o banco de dados. Então sim, diferentes “tipos” de fonte de dados. ( é que para mim o tipo está incluso da def de fonte de dados)

Não necessáriamente. Se vc inclui o banco em todos os testes vc inclui um overhead desnecessário. A menos que vc não confie no seu ORM não ha necessidade dessas chamadas todas. Se vc não confia realmente no ORM vc faz testes apenas relativos ao ORM e não do resto do sistema.
Além disso vc deve ter testes de integração e ai sim todo o processo é exercitado. Mas para criar classes e ver se elas funcionam comunicar com o banco pode ser overkill.

Não tão rápido … Fazer um select para paginação em SQLServer é bem diferente do que para Postgress. O DAO é suposto encapsular esta diferença. Então mesmo para fontes do mesmo tipo (“banco de dados”) ainda precisa ter diferentes implementações. ( Claro, com um design bom, vc minimiza essas implementações repetitivas , pelo uso de dialectos, por exemplo, mas mesmo assim …).
O ponto é que no geral vc sim precisa mudar de DAO (aliás é para isso que ele serve). NO caso particular e dependendo da sua arquitetura e maturidade do seu framework de negocio / applicação pode não ser necessário. Dizer que não é necessário sempre, é ir longe demais.

sergiotaborda

Tudo isso é resolvido facilmente se você não programar para banco de dados. Se vc programar para interfaces e via OO esse problema não se coloca.

Y

Acho que eu entendi o texto diferente de voce, Sergio. Pelo que entendi o autor se refere ao encapsulamento prematura daquilo que nao precisa ser encapsulado. Sem pensar nos porques do que esta sendo feito.

Por exemplo, (e eu mesmo ja defendi essa pratica aqui) por que eu preciso de toda a abstracao e encapsulamento das camadas de acesso a dados definidas pelo padrao DAO, se os proprios frameworks ORM ja me dão esse encapsulamento, o unico cuidado que eu preciso é nao misturar os codigos dessas apis com as minhas regras. Mas nao creio que seja isso que foi indicado no texto.

Talvez eu tenha lido de forma relapsa, mas a intencao do autor era indicar o porque de encapsular o que ja esta encapsulado, era de criticar o fato de se fazer alguma coisa só porque em algum lugar se leu que é assim, sem questionar, sem testar outras formas, sem buscar outras solucoes. E essa é a coisa que mais vejo por ai. Vou encapsular porque diz que encapsular é certo. E essas coisas nos levam a encontrar, como encontrei, uma aplicacao dividida em duas pra encapsular a regra num web service, que jamais sera usado em outra aplicacao, apenas pra separar apresentacao da logica.

L

Eu já li um texto que toca mais ou menos nesse assunto, mas se chama Premature Flexibilization Is The Root of Whatever Evil Is Left. Basicamente, é a atitude de deixar as coisas muito complexas sobre o pretexto de deixar flexível, só que a própria complexidade se torna fonte de rigidez.

Eu não acho errado o DAO, acho errado outras coisas que o pessoal faz com persistência, do tipo: gerar DAO em cima do Hibernate, ou então criar um DAO genérico…

Ou pior ainda, para cada tabela do banco, criar um CRUD pro usuário. Ora, CRUD é raro num sistema bem feito e se localiza mais ou em conceitos que não são o core ou em configurações. Os outros casos são regras de negócio que contém algum tipo de operação de persistência, mas que fica oculto para o usuário. O problema é que basicamente os programadores preferem seguir um script previsível de menus com “inserir blablablá”, “alterar blablablá”, “consultar blablablá” e “remover blablablá”, esquecendo até mesmo que o usuário não pensa em termos de banco de dados. Um sistema com apresentação ao usuário ruim desse jeito, não vale nem a pena criar DAOs para encapsular regra do banco. O programador expôs o banco ao usuário!

Quando ocorre uma preocupação da necessidade do usuário, e o sistema usa termos familiares, não dos desenvolvedores, mas de quem a utiliza. É natural aparecer a famosa “regra de negócio”, onde se percebe que é esquisito misturr essas regras com acessos “crus” de banco. O DAO passa a ser uma solução natural para resolver isso.

Alexandro.Almeida

Sendo simplista:
Use um ORM (JPA/TopLink/Hibernate/etc), e implemente todo o acesso aos dados no repository usando o seu ORM.

Pronto falei!!

ViniGodoy

Eu estava me referindo a Postre e SQLServer como fontes de dados diferentes.

Y

Como eu disse, eu ja precisei fazer essa migracao num sistema relativamente complexo. Foi feito sem traumas, mas gracas ao hibernate, nao gracas aos daos. E claro, eu tinha controle absoluto sobre os esquemas dos bancos.

Se tivesse sido feito diretamente com JDBC o trabalho seria bem maior, por mais que eu tivesse aplicado o padrao da maneira indicada e nao sei o que mais, ainda assim eu teria que reimplementar todos os daos, um a um. Eu, com certeza precisaria ter a hierarquia SqlServerDAO e PostgreDAO, e nao tem nada de facil nisso.

Acho que esses “root of all evil” que tem surgido. Otimizacao, flexibilizacao, encapsulamento, vem apenas confirmar uma regra primaria do Extreme Programming: KISS (keep it simple, stupid).

Editado só pra conclusao:
O que me dá medo mesmo são as más interpretações dessas coisas.

Y

sergiotaborda:
Não vou acessar o banco real durante os testes, nem me vou dar ao trabalho de ter um banco de testes. Eu não estou testando o acesso ao banco (eu confio no jdbc) e sim as features do sistema. Então é comum utilizar algum tipo de objecto que encapsula o acesso a dados ( não necessáriamente um DAO ou um DomainStore) e posso mudar sem causar problemas no resto da aplicação.

Fugindo um pouco do assunto principal do topico, mas nao pude deixar de notar.

Com um banco de testes voce nao vai testar o jdbc, vai testar se seu esquema e se seu mapeamento objeto-relacional estao corretos, vai manter os testes la para que eles indiquem que continuam corretos a cada alteracao no modelo de objetos ou no esquema do banco. E voce nao pode fazer isso no seu banco de desenvolvimento, menos ainda no de producao, porque nao vai conseguir manter os dados sempre no mesmo estado para que os testes seja realizadao. Entao é fundamental que haja um banco de testes.

Do contrario seus dados nao existem (baseado na afirmacao de que uma funcionalidade só existe se existe um teste pra ela).

sergiotaborda

YvGa:
sergiotaborda:
Não vou acessar o banco real durante os testes, nem me vou dar ao trabalho de ter um banco de testes. Eu não estou testando o acesso ao banco (eu confio no jdbc) e sim as features do sistema. Então é comum utilizar algum tipo de objecto que encapsula o acesso a dados ( não necessáriamente um DAO ou um DomainStore) e posso mudar sem causar problemas no resto da aplicação.

Fugindo um pouco do assunto principal do topico, mas nao pude deixar de notar.

Com um banco de testes voce nao vai testar o jdbc, vai testar se seu esquema e se seu mapeamento objeto-relacional estao corretos, vai manter os testes la para que eles indiquem que continuam corretos a cada alteracao no modelo de objetos ou no esquema do banco.

Mas afinal você está testando a sua aplicação ou o seu uso do framework X ?
Como eu disse , ou vc confia no ORM que usa, ou não confia. Para testar uma funcionalidade de transação de conta vc precisa de banco de dados ?
Para quê ? Para ter a certeza que ficou gravado ? Ora, o ponto não saber se ficou gravo, é saber se os valores são corretos. E para isso não precisa de um banco de dados. Ou melhor, vc precisa de um banco de dados (definição formal) mas não de um SGDB.

Em sistema orientados a dados até poderia concorda contigo, mas em sistemas direcionados ao tratamento de entidades , não.
Não é fundamental ter um banco de dados SGDB. Um map ou um list resovlem a maior parte dos testes.
Mas como falei antes, se não confia no seu ORM, então, ok, por todos os meios use um banco de dados. Só se lembre de cumprir o mandato de testes que implica em que o estado antes e depois do teste tem que ser o mesmo. i.e. não se esqueça de apagar o que gravou de novo ou gravar o que apagou durante o teste. Agora… vc acha que esse tipo de controle de consistência do banco é algo fundamental ? Eu não acho. Acho chato e sem propósito ( mesmo com DBUnit é melhor não precisa do DBUnit).

Adendo:
O conceito de banco de testes só existe poruqe vc usa o hibernate/jpa que não são domianstores verdadeiros no sentido que não permitem escrever/ler para outos formatos. Se vc tiver um framework com esse poder, vc não vai precisar ter um banco de dados.

Um exemplo muito facil de eliminar o banco durante os testes é usar mocks de repositorios. Como as interfaces do repositorio são simples e orientadas ao dominio implementar o retorno é trivial a maior parte das vezes. Muito mais simples que ficar codificando DAO , DBUnit ou qualquer outra tecnica que teimosamente usa o banco de dados.

Y

Nao estou testando o framework X, estou testando se fiz o mapeamento correto. Pois pode acontecer, depois que o sistema estiver em producao eu precisar alterar qualquer coisa no meu codigo e tudo funcionar perfeitamente, a regra aplicada corretamente, a integridade do estado dos objetos mantida, todo ciclo de vida devidamente mantido, mas cinco minutos depois que eu gero a versao para o cliente ele me liga dizendo que a tela tal parou de funcionar. Aí, depois de ver o log de erro eu descubro que esqueci de alterar o mapeamento. Ou entao, pior ainda, esqueci de alterar o modelo de dados para a alteracao que eu fiz.

Se eu tivesse um banco de testes, utilizando testes unitarios eu teria reduzido bastante a probabilidade disso acontecer.

DBUnit é para testar o banco, se o esquema esta correto, se sua classe esta sendo mapeada corretamento para o banco, nao outra coisa. Tudo isso que voce disse tem que ser feito, mas alem disso o esquema e o mapeamento TÊM que ser testados.

sergiotaborda

YvGa:

Tudo isso que voce disse tem que ser feito, mas alem disso o esquema e o mapeamento TÊM que ser testados.

O ponto é que não precisam ser testados a todo o momento. Existem vários niveis para os testes. Esse tipo de coisas é testada em teste de integração que rodam pouco frequentemente em relação aos teste com foco em desenvolver features.

B

Concordo com o sérgio, testar a persistência tem a sua hora e lugar. Testá-lo toda hora deixa o processo de build extremamente lento em projetos maiores.

aleck

sergiotaborda:

O ponto é que não precisam ser testados a todo o momento. Existem vários niveis para os testes. Esse tipo de coisas é testada em teste de integração que rodam pouco frequentemente em relação aos teste com foco em desenvolver features.

Então vc tem um teste de integração com o banco de dados e trata os erros provenientes da disponibilidade do servidor ou apenas confia?

De qualquer forma, sou a favor de usar ferramentas como o dbunit. Pela experiência que tenho, quanto mais distanciarmos o desenvolvimento do ambiente real maiores serão os problemas na hora da entrega.

Y

Concordo plenamente. Mas eles têm que existir e têm que ser executados toda vez que ha uma alteracao no esquema do banco ou no mapeamento.

Claro que se voce executar esses testes junto com os testes do dominio vai acabar mais cedo ou mais tarde inviabilizando os testes.

Thiago_Senna

Rubem, deixe eu tomar seus exemplos emprestado para opinar neste tópico! :wink:

Rubem Azenha:
Eu uso DAO para não ter código de Hibernate/JPA/ETC espalhado pela aplicação inteira.

prefiro ter um DAO e fazer

findByXPTO

do que

q = em.createQuery("asdadasdasda");
q.setParameter(112321,1231231);
q.setParameter(112321,1231231);
q.setParameter(112321,1231231);
q.setParameter(112321,1231231);
q.getResultList();

IMHO, uma opção para tirar o DAO fora e ainda ter um codigo bacana seria, por exemplo:

FindByXPTO find = new FindByXPTO(session);
List<XPTO> list = find.list();

O exemplo é simples, mas acredito que seja suficiente pra demonstrar outras maneiras de organiar o codigo e mantê-lo legível. Claro que o mais comum é usar um DAO, mas dependendo do tamanho do projeto prefiro evitar a criação de uma interface para o DAO e sua respectiva implementação.

Eu já venho evitando DAO’s em meus projetos pessoais. O mais comum é eu usar repositórios para abstrair o local onde guardo as entidades, no entanto, não são todos os projetos que necessitam de idéias como DDD e seu famoso repositório.

O framework apache click, um framework ‘component-based’, tem alguns exemplos onde as ações CRUD para persistência já está embutida nos proprios componentes de UI. Outro framework interessante é o Databinder, que também incorporou chamadas de persistências em seus componentes de UI.

A parte difícil, em minha opinião, é que ao abandonar os DAO’s você acaba saindo fora do senso comum. Agora você terá que usar sua criatividade, estudar novos patterns e métodos para abrir mão do DAO e manter o codigo legível.

Segue algumas referências abaixo:
http://svn.apache.org/repos/asf/incubator/click/trunk/examples/click-cayenne/


http://databinder.net/site/show/overview

Y

Rubem Azenha:
Eu uso DAO para não ter código de Hibernate/JPA/ETC espalhado pela aplicação inteira.

prefiro ter um DAO e fazer

findByXPTO

do que

q = em.createQuery("asdadasdasda");
q.setParameter(112321,1231231);
q.setParameter(112321,1231231);
q.setParameter(112321,1231231);
q.setParameter(112321,1231231);
q.getResultList();

Esse tipo de interpretacao que me da medo. O Rubem, apesar de ter interpretado errado o texto (ou eu o fiz), demonstrou que tem experiencia suficiente pra nao fazer dessa forma que ele entendeu.

Mas muita gente que esta lendo esse topico pode ter interpretado do mesmo jeito que ele e vai sair por ai fazendo as coisas como na opcao 2 do Rubem. Mas nao é a isso que o texto se refere. Ou fui eu que nao entendi.

O que tem sido feito é usar interface do repositorio->implementacao do repositorio->interface dao->implementacao de um dao generico->subclasse do dao generico->api do framework de persistencia.

Quando simplesmente interface repositorio->implementacao repositorio->api framework ja resolve.

Eu trabalho numa empresa que nao incentiva boas praticas de programacao e ouco diariamente distorcoes absurdas de padroes. Por isso me arrepiam textos desse tipo.

Esses dias, tentando interpretar um codigo praticamente ilegivel, num metodo com dezenas de linhas e variaveis com nomes sem pé nem cabeca eu perguntei ao autor porque nao poe comentario pelo menos e ele me diz que comentario é anti-pattern. Como ele nao eh meu subordinado, alias o cargo dele eh o mesmo que o meu, só pude dar risada e enfiar o nariz no codigo pra decifrar.

É um tal de separar apresentacao de logica com web service, nao por comentario porque é anti-pattern. dizer que código bem feito nao precisa de teste. Tanto que criei pavor desses textos porque tenho certeza que eles vao cair em maos erradas.

Criado 15 de julho de 2009
Ultima resposta 16 de jul. de 2009
Respostas 26
Participantes 13