<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Rodrigo Allemand</title>
	<atom:link href="http://blog.rodrigoallemand.com.br/?feed=rss2" rel="self" type="application/rss+xml" />
	<link>http://blog.rodrigoallemand.com.br</link>
	<description>Expressando a minha opinião</description>
	<lastBuildDate>Fri, 16 Oct 2009 14:43:31 +0000</lastBuildDate>
	<generator>http://wordpress.org/?v=2.9.2</generator>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
			<item>
		<title>DDD encapsula a minha Regra de Negócio</title>
		<link>http://blog.rodrigoallemand.com.br/?p=186</link>
		<comments>http://blog.rodrigoallemand.com.br/?p=186#comments</comments>
		<pubDate>Fri, 16 Oct 2009 14:34:26 +0000</pubDate>
		<dc:creator>Rodrigo Allemand</dc:creator>
				<category><![CDATA[DDD]]></category>
		<category><![CDATA[Desenvolvimento]]></category>
		<category><![CDATA[Regras de Negócio]]></category>

		<guid isPermaLink="false">http://blog.rodrigoallemand.com.br/?p=186</guid>
		<description><![CDATA[Resolvi responder ao comentário do Diogo (no post Blindando o Domínio) em um post separado por achar que essa é a duvida mais frequente que eu vejo, seja em conversas informais, fóruns, palestras, etc.
Onde colocar as minhas regras de negócio?
A resposta é&#8230;. Depende! rs
Se você escolheu utilizar DDD no seu projeto é porque você conhece [...]]]></description>
			<content:encoded><![CDATA[<p>Resolvi responder ao comentário do Diogo (no post <a href="http://blog.rodrigoallemand.com.br/?p=141" target="_blank">Blindando o Domínio</a>) em um post separado por achar que essa é a duvida mais frequente que eu vejo, seja em conversas informais, fóruns, palestras, etc.</p>
<p style="text-align: center;"><strong>Onde colocar as minhas regras de negócio?</strong></p>
<p style="text-align: center;"><strong></strong>A resposta é&#8230;.<strong> Depende! </strong>rs</p>
<p>Se você escolheu utilizar DDD no seu projeto é porque você conhece e já isolou o problema a ser resolvido que, por ser complexo, será baseado em um modelo, recebendo o foco e a prioridade necessárias para a solução deste domínio.  Quando você isola este domínio, obviamente você deve encapsular tambem todas as regras de negócio dentro desse domínio.</p>
<p>Para exemplificar melhor vamos fazer a seguinte funcionalidade de exemplo no nosso dóminio.</p>
<blockquote><p>Todos os pedidos com valor acima 1.000,00 e que são pagos com dinheiro em espécie são <em>elegíveis</em> a um desconto de 10% por produto.</p></blockquote>
<p>Claro que esta informação tem que ser passada para o usuário final do sistema, mas é responsabilidade do sistema checar se as informações passadas estão corretas.  Você pode até colocar a regra de validação <strong>tambem</strong> na camada de apresentação ou dentro do seu banco de dados em forma de triggers (argh, rs!), mas de qualquer maneira <strong>o domínio tem que ter esta validação</strong>, já que um dos princípios do DDD é justamente poder trocar a camada de apresentação sem que o domínio seja alterado ou compartilhar o mesmo domínio entre interfaces/sistemas diferentes.</p>
<p>Portanto, segue a primeira afirmação:</p>
<blockquote><p>Por mais que a sua camada de apresentação faça as regras necessárias para uma determinada funcionalidade, o seu domínio tambem deve, obrigatoriamente, fazer com que estas regras estejam presente internamente, tornando-o coeso da camada que ele comunica.</p></blockquote>
<p>Vamos melhorar este exemplo mostrando como ficariam as entidades envolvidas nesta funcionalidade.</p>
<pre name="code" class="java">
public class Pedido {
	private List&lt;ItemPedido&gt; itens;
	private BigDecimal precoTotal;
	//Acessores omitidos
}
public class ItemPedido {
	private Produto produto;
	private BigDecimal precoVenda;
	private BigDecimal desconto;
	//Acessores omitidos
}
</pre>
<p><em>OBS.: Muitos podem perguntar porque a informação referente ao preço final é um atributo da classe e não um comportamento da entidade (um método que poderia somar todos os preços finais decrementando os descontos dados por cada produto, multiplicado pela quantidade de cada produto). Vamos pensar que o preço do Produto pode &#8211; e deve &#8211; variar e o sistema precisa manter a informação do preço de venda naquele momento, ok?</em></p>
<p>Eu encaro que esta regra de negócio deve estar em uma checagem no momento da inclusão, como por exemplo uma Specification destinada somente a esta regra. Lembro que, a Specification tem, neste caso, o intúito de validar uma informação e que ela não precisa ser necessariamente apenas uma única specification. Eu posso &#8211; e é até melhor &#8211; dividir a informação em várias Specifications, uma para cada regra de negócio que a minha funcionalidade exige.</p>
<p>Vamos pensar então que a minha classe ValidarDescontoDadoSpecification tem o seguinte código:</p>
<pre name="code" class="java">
public class ValidarDescontoDadoSpecification
	implements Specification&lt;ItemPedido&gt; {

	public static final BigDecimal DESCONTO_MAXIMO_PGTO_DINHEIRO = 10;

	public boolean isSatisfiedBy(ItemPedido item){
		if(itemPedido.getFormaPagamento.equal(FormaPagamento.DINHEIRO){
			BigDecimal descontoDado =
				Calculadora.percentualEntre(
					item.getPrecoVenda(),
					item.getDesconto());
			if(descontoDado.compareTo(DESCONTO_MAXIMO_PGTO_DINHEIRO) &gt; 1){
				//É necessário comunicar ao domínio o porque da falha
				//Neste caso, leia mais sobre Notification
				return false;
			}
		}
		return true;
	}
}
</pre>
<p>Pensando que você sempre salva o pedido, poderiamos ter uma outra Specification para isso, conforme abaixo:</p>
<pre name="code" class="java">
public class PersistirPedidoSpecification
	implements Specification&lt;Pedido&gt; {

	public boolean isSatisfiedBy(Pedido pedido){
		/*
		  As boas maneiras de aplicativos internet diz que
		  vc deve validar tudo de uma unica vez, rs
		*/
		boolean resultado = true;

		//Validações referente ao Pedido

		ValidarDescontoDadoSpecification spec =
			new ValidarDescontoDadoSpecification();
		for(ItemPedido item : pedido.getItens()){
			if(!spec.isSatisfiedBy(item)){
				/*
				  Lembre que a informação da falha deve ser feita
				  pela outra Specification, não por esta!
				*/
				resultado = false;
			}
		}
		return resultado;
	}
}
</pre>
<p>Assim, no final de tudo, nós poderiamos ter no repositório Pedidos, o seguinte código:</p>
<pre name="code" class="java">
public class Pedidos{

	public static void persistir(Pedido pedido){
		PersistirPedidoSpecification spec
			=  new PersistirPedidoSpecification();
		if(spec.isSatisfiedBy(pedido){
			dao.salvar(pedido);
		} else {
			//Comunica a falha encontrada às outras camadas
		}
	}
}</pre>
<p>Espero ter ajudado!!!</p>
<p>Abraço a todos!!!</p>
<p>Comente e Recomende!!</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.rodrigoallemand.com.br/?feed=rss2&amp;p=186</wfw:commentRss>
		<slash:comments>13</slash:comments>
		</item>
		<item>
		<title>O Cliente tem sempre razão&#8230; o usuário nem sempre!</title>
		<link>http://blog.rodrigoallemand.com.br/?p=182</link>
		<comments>http://blog.rodrigoallemand.com.br/?p=182#comments</comments>
		<pubDate>Thu, 24 Sep 2009 19:43:47 +0000</pubDate>
		<dc:creator>Rodrigo Allemand</dc:creator>
				<category><![CDATA[Matodologia Agil]]></category>
		<category><![CDATA[Desenvolvimento]]></category>
		<category><![CDATA[Estória]]></category>
		<category><![CDATA[Metodologia Agil]]></category>
		<category><![CDATA[Requisito]]></category>

		<guid isPermaLink="false">http://blog.rodrigoallemand.com.br/?p=182</guid>
		<description><![CDATA[Muitas coisas fazem um projeto passar de sucesso a um completo fracasso, dentre eles uma equipe mau escolhida, um escopo não casado com os prazos, uma arquitetura ruim, etc. Mas um dos maiores problemas que eu vejo que pode transformar um &#8220;felizes para sempre&#8221; em um &#8220;problema para sempre&#8221; é o levantamento das necessidades e [...]]]></description>
			<content:encoded><![CDATA[<p>Muitas coisas fazem um projeto passar de sucesso a um completo fracasso, dentre eles uma equipe mau escolhida, um escopo não casado com os prazos, uma arquitetura ruim, etc. Mas um dos maiores problemas que eu vejo que pode transformar um &#8220;felizes para sempre&#8221; em um &#8220;problema para sempre&#8221; é o levantamento das necessidades e requisitos.</p>
<p>Mais uma vez, muitos podem ser os fatores que atrapalham um bom levantamento. Analistas inexperientes, hierarquias mau definidas, credibilidade da equipe, clima hostil com o cliente, falha de detalhamento &#8211; muito ou pouco, dependendo do caso, usuários indecisos, usar &#8220;o que já existe&#8221; como exemplo e o pior de todos: usuários &#8220;acostumados&#8221; com o erro.</p>
<p>Recentemente, estou trabalhando como bombeiro em um projeto que espelha muito do dito acima.</p>
<p>A proposta era redesenhar um sistema originalmente feito em Delphi, que já funcionava a alguns anos para uma estrutura web em Java que temos. Este sistema já tinha passado por diverss atualizações, transformando o código em uma bela macarronada</p>
<p>Por uma briga que se arrasta a gerações (rs), há um clima hostil entre o gerente de projetos e o cliente final (que não cabe a mim questionar, muito menos entender). Isso gerava muitas discursões (infinitas até) quando se queria definir algum ponto.</p>
<blockquote><p>Dica 1:Quando o manifesto ágil diz para ter o cliente como parte da equipe não é so ter o cliente por perto, mas sim jogando no mesmo time.</p></blockquote>
<p>Quando se senta para definir alguma coisa, quanto mais gente entendendo, melhor! Entendendo não significa estar falando ou questionando. Mas todas pessoas precisam ter o mesmo entendimento. Por muitas vezes na reunião, surgia uma pergunta que não tinha fundamento algum, como se a pessoa estivesse voando ou não entendendo nada do que estava acontecendo.</p>
<blockquote><p>Dica 2: Nunca deixe uma duvida no ar. A reunião é justamente para atender as necessidades dos analistas. Preste atenção quando alguem fala para poder perguntar alguma coisa válida. E questione se não entender! Sempre!</p></blockquote>
<p>Para piorar, o gerente teve uma das piores atitudes que se pode tomar em uma reunião de levantamento: proibir os analistas de perguntarem, fazendo ele um funil com o cliente. Esta atitude fez com que conceitos fossem perdidos e o pior, conceitos errados surgiram.</p>
<blockquote><p>Dica 3: Para um projeto, hierarquias não devem existir. Claro que algumas vozes pesam mais do que outras mas no momento de levantamento, todos devem ser ouvidos.</p></blockquote>
<p>Então começa a definição dos casos de uso. Envolvidos em conceitos errados, climinhas e muita briga, os analistas &#8216;copiaram&#8217; as funcionalidades do sistema antigo sem propor nenhuma alteração. Na aprovação do documento de requisito (aqui nós temos esse passo, por enquanto, rs) o usuário reclamou de muita coisa que estava definida ali, dizendo que se fosse par ter a mesma coisa, que continuasse com o antigo.</p>
<blockquote><p>Dica 4: O legado pode ser usado como exemplo, mas <span style="text-decoration: line-through;">tente</span> sempre surpreenda o cliente com alguma novidade. Pense no que pode melhorar o trabalho dele e proponha modificações, sempre embasadas em alguma teoria, por mais simples que seja.</p></blockquote>
<p>Troca-se a equipe para dar mais força ao projeto. Com isso, o usuário já não acreditava na equipe anterior, achando que eles poderiam novamente fazer as besteiras feitas anteriormente.</p>
<blockquote><p>Dica 5: Por mais que fosse necessária a colocação de mais recursos, nunca deixe a credibilidade da equipe em risco. Se você não acredita no vendedor, como vai comprar o produto?</p></blockquote>
<p>A nova equipe começou a detalhar &#8211; novamente &#8211; as funcionalidades e as mesmas tiveram variações, fazendo com que coisas com pouco detalhe tivessem uma pontuação de &#8216;codificação&#8217; errada diante de tantos detalhes e outras que realmente tinham um alto grau de dificuldade, com pontuações baixas diante da falta de detalhamento.</p>
<blockquote><p>Dica 6: Detalhe somente o necessário. Incremento é justamente isso! <span style="text-decoration: line-through;">Se</span> Quando chegar o momento você aumentará o nivel de detalhe.</p></blockquote>
<p>Dá pra sentir como foi a fase de desenvolvimento deste projeto, <em>né</em>?!</p>
<p>Fazendo uma analogia com a construção de uma casa, a reunião de apresentação dos requisitos e das datas de entrega foi mais ou menos assim.</p>
<p><strong>Analista:</strong> <em>(&#8230;) Então aqui nós teremos os 3 quartos necessários.</em><br />
<strong>Usuário:</strong> Mas eu não preciso de 3 quartos. Eu preciso de 3 camas!<br />
<strong>Analista:</strong> <em>Sim mas nós colocamos 3 quartos distintos para uma melhor modularização. Sem contar que esse quarto maior aqui é uma suite.</em><br />
<strong>Usuário:</strong> Mas nesse quarto aqui, alem de ser suite, ele precisa de uma cozinha.<br />
<strong>Analista:</strong> <em>Como assim uma cozinha? Já existe uma cozinha aqui, veja!</em><br />
<strong>Usuário:</strong> Mas eu preciso de uma cozinha aqui porque na antiga casa eu tinha uma cozinha perto da cama.<br />
<strong>Analista:</strong> <em>Sim, mas agora nós temos quartose a cozinha em ambientes separados.</em><br />
<strong>Usuário:</strong> (&#8230;) E onde está a minha janela dos fundos para eu entrar?<br />
<strong>Analista:</strong> <em>Agora nós temos uma porta aqui nos fundos.</em><br />
<strong>Usuário:</strong> Está errado. Funcionava assim: eu entrava na casa, abria a janela, saia da casa, dava a volta na casa, entrava pela janela e acessava a parte dos fundos da casa.<br />
<strong>Analista:</strong> <em>Agora você não vai precisar fazer isso. Nós temos uma porta para que você entre diretamente por ela, já que o proposito é apenas entrar na casa.</em><br />
<strong>Usuário:</strong> Não o proposito é entrar <span style="text-decoration: underline;">na casa pela janela</span>. <span style="text-decoration: underline;">E janela não é porta</span>. A porta é pra entrar pela frente, a janela é para entrar pelos fundos.</p>
<blockquote><p>Dica 6: Para o usuário que está acostumado com o erro do software antigo (que para ele já é trivial &#8220;entrar por uma janela&#8221;), você precisa mostrar e provar para o usuário que se é para entrar, precisa ser por uma porta.</p></blockquote>
<p>Como dizia meu avô&#8230;</p>
<blockquote><p>Burro não aprende, burro acostuma.<br />
Não faça do seu usuário um burro.</p></blockquote>
<p>Comente e Recomende!</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.rodrigoallemand.com.br/?feed=rss2&amp;p=182</wfw:commentRss>
		<slash:comments>3</slash:comments>
		</item>
		<item>
		<title>DDD &#8211; Fabricando e Encontrando Objetos</title>
		<link>http://blog.rodrigoallemand.com.br/?p=166</link>
		<comments>http://blog.rodrigoallemand.com.br/?p=166#comments</comments>
		<pubDate>Mon, 17 Aug 2009 20:36:13 +0000</pubDate>
		<dc:creator>Rodrigo Allemand</dc:creator>
				<category><![CDATA[DDD]]></category>
		<category><![CDATA[Factory]]></category>
		<category><![CDATA[Fowler]]></category>
		<category><![CDATA[Registry]]></category>
		<category><![CDATA[Singleton]]></category>

		<guid isPermaLink="false">http://blog.rodrigoallemand.com.br/?p=166</guid>
		<description><![CDATA[Antes de mais nada, este post não é &#8211; como nenhumk dos outros desta série &#8211; focado extritamente em DDD. Leia o primeiro post da séries para entender melhor&#8230;


Em qualquer sistema OO, vc trabalha com&#8230;.. objetos (ohhhhhhhh)
Qualquer objeto &#8216;precisa&#8217; ser&#8230;.. criado antes de ser utilizado&#8230;. (ohhhhhhh)
Qual a melhor maneira de se criar objeto? (errr&#8230;. humm&#8230;.. [...]]]></description>
			<content:encoded><![CDATA[<p style="text-align: left;"><em><strong>Antes de mais nada, este post não é &#8211; como nenhumk dos outros desta série &#8211; focado extritamente em DDD. Leia o primeiro post da séries para entender melhor&#8230;</strong></em></p>
<p style="text-align: left;">
<p style="text-align: left;">
<p style="text-align: center;"><em>Em qualquer sistema OO, vc trabalha com&#8230;.. objetos <strong>(ohhhhhhhh)</strong></em></p>
<p style="text-align: center;"><em>Qualquer objeto &#8216;precisa&#8217; ser&#8230;.. criado antes de ser utilizado&#8230;. <strong>(ohhhhhhh)</strong></em></p>
<p style="text-align: center;"><em>Qual a melhor maneira de se criar objeto? <strong>(errr&#8230;. humm&#8230;.. bem&#8230;&#8230;.)</strong></em></p>
<p style="text-align: center;">
<p style="text-align: center;">
<p>Muitas são as maneiras&#8230; usando um construtor, por DI (Dependency Injection), por fábricas, etc.</p>
<p>O mais utilizado são as fábricas, ou Factories conforme catalogado pelo GoF, ou Gang of Four.</p>
<blockquote><p>Resumidamente, &#8220;<span style="font-family: Trebuchet MS;">o padrão Factory fornece uma interface para a  criação de famílias de objetos correlatos ou dependentes sem a necessidade de  especificar a classe concreta destes objetos&#8221;.</span></p></blockquote>
<p><a href="http://www.guj.com.br/article.show.logic?id=137" target="_blank">Diversos</a> <a href="http://www.macoratti.net/vbn5_dp1.htm" target="_blank">exemplos</a> de <a href="http://www.guj.com.br/posts/list/74360.java" target="_blank">fábricas</a> <a href="http://www.dofactory.com/Patterns/PatternFactory.aspx" target="_blank">existem</a> <a href="http://www.web4u.eti.br/2009/02/02/design-pattern-factory-enum/" target="_blank">espalhados</a> pela <a href="http://gsraj.tripod.com/design/creational/factory/factory.html" target="_blank">internet</a>, e <a href="http://cristianspace.wordpress.com/2007/11/02/design-patterns-factory-method/" target="_blank">eu não vou</a> <a href="http://www.allappforum.com/java_design_patterns/factory_pattern.htm" target="_blank">colocar</a> <a href="http://en.wikipedia.org/wiki/Factory_method_pattern" target="_blank">mais um</a> <a href="http://msdn.microsoft.com/en-us/library/ms954600.aspx" target="_blank">aqui</a>. <a href="http://www.google.com.br/#hl=pt-BR&amp;q=factory+design+pattern&amp;btnG=Pesquisa+Google&amp;meta=&amp;aq=f&amp;fp=bccb46dee709e962" target="_blank">Procure</a>, rs!</p>
<p>A motivação inicial do padrão era a criação de objetos complexos, fazendo com que a lógica estivesse toda em um unico lugar&#8230; princípio de <a href="http://en.wikipedia.org/wiki/Don%27t_repeat_yourself" target="_blank">DRY</a> nos promórdios da Arquitetura de Software!</p>
<p>Porém, certos objetos alem de serem complexos, precisavam de um processo de construção demorado. Algumas tecnicas para a sulução deste problema era &#8216;reter&#8217; o objeto contruido e utilizá-lo como um ponto de acesso único, otimizando assim o processo de construção.</p>
<p>Com isso, por muitas vezes os desenvolvedores juntavam dois padrões de projetos para sanar o problema de contrução complexa e demorada, utilizando Factory e &#8216;Singletons&#8217; para colocar objetos a disposição do &#8216;domínio&#8217;.</p>
<p>Colocar fábricas a disposição dos desenvolvedores, por muitas vezes, mascarava onde realmente estes objetos deveriam ser criados. Poderiam existir inúmeras fábricas em um único projeto, como eu já presenciei num passado não muito distante. Era DaoFactory pra cá, AbstractDaoFactory pra lá, ReportFactory aqui e ServiceFactory acolá! Uma verdadeira macarronada de factories!</p>
<p>Então, como manter um ponto único de acesso para &#8216;encontrar&#8217; os objetos?</p>
<p>Fowler resolveu colocar tudo em um unico padrão e o nomeou de Registry, ou Registro.</p>
<p><a href="http://martinfowler.com/eaaCatalog/registry.html" target="_blank">De acordo com Fowler, Registry é</a></p>
<blockquote><p>Um objeto conhecido que outros objetos podem usar para encontrar objetos e serviços comuns.</p></blockquote>
<p>A função do Registro é:</p>
<ol>
<li>Criar objetos</li>
<li>Encapsular complexidades de criação</li>
<li>Reter objetos criados</li>
<li>Funcionar como &#8216;local dos objetos&#8217;</li>
</ol>
<p>Com isso, se você quizer saber ou precisar de um objeto e o seu sistems tem um Registro, pergunte a ele!</p>
<p>Normalmente os Registros são factories e singletons mesclados, conforme o exemplo abaixo:</p>
<pre name="code" class="java">public MyDomainRegistry{
    private static MyDomainRegistry INSTANCE = null;

    private MyDomainRegistry(){
        loadVariables();
    }

    private static MyDomainRegistry instance(){
        //Coloque aqui a sua implementação de Singleton
        return INSTANCE;
    }

    //Posso usar SubDomains
    private ConsultarSubDomain consultarSubDomain;
    //Posso usar Services Services
    private ConversaoService conversaoService;
    //Qualquer objeto que eu queira localizar!
    private MyRepository myRepository;

    private void loadVariables(){
        //Aqui vc deve criar os seua objetos como achar melhor
        this.consultarSubDomain = new ConsultarSubDomain();
    }

    //Aqui vc coloca os métodos estáticos para retornar
    //os objetos que o registro precisa controlar
    public static ConsultarSubDomain consultarSubDomain() {
        return instance().consultarSubDomain;
    }
}</pre>
<p>Bem simples, não?</p>
<p>Agora, para você utilizar um objeto, basta solicitar ao registro, assim.</p>
<pre name="code" class="java">public class FachadaDoDominio {

    private FachadaDoDominio() {
    }

    public static ConsultarSubDomain consultar(){
        return MyDomainRegistry.consultarSubDomain();
    }
}</pre>
<p>Comente e Recomende!</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.rodrigoallemand.com.br/?feed=rss2&amp;p=166</wfw:commentRss>
		<slash:comments>5</slash:comments>
		</item>
		<item>
		<title>De Padawan a Jedi</title>
		<link>http://blog.rodrigoallemand.com.br/?p=163</link>
		<comments>http://blog.rodrigoallemand.com.br/?p=163#comments</comments>
		<pubDate>Mon, 10 Aug 2009 13:46:50 +0000</pubDate>
		<dc:creator>Rodrigo Allemand</dc:creator>
				<category><![CDATA[Desenvolvimento]]></category>
		<category><![CDATA[Livros]]></category>
		<category><![CDATA[PragProg]]></category>

		<guid isPermaLink="false">http://blog.rodrigoallemand.com.br/?p=163</guid>
		<description><![CDATA[Recentemente um desenvolvedor da minha equipe e eu estavamos conversando sobre como dar soluções bem feitas. Ele se queixava de demorar muito para achar uma solução, construindo e re-construindo por muitas vezes um determinado pedaço de código até chegar a uma solução realmente boa. Refactoring é a saida para um bom código, mas existem outos [...]]]></description>
			<content:encoded><![CDATA[<p>Recentemente um desenvolvedor da minha equipe e eu estavamos conversando sobre como dar soluções bem feitas. Ele se queixava de demorar muito para achar uma solução, construindo e re-construindo por muitas vezes um determinado pedaço de código até chegar a uma solução realmente boa. Refactoring é a saida para um bom código, mas existem outos pontos de falha na sua maneira de programar.</p>
<p>O conhecimento hoje é uma jóia que está a apenas alguns cliques de todos nós. Hoje em dia se aprende desde a <a href="http://www.google.com.br/search?q=como+fazer+arroz&amp;ie=utf-8&amp;oe=utf-8&amp;aq=t&amp;rls=org.mozilla:pt-BR:official&amp;client=firefox-a" target="_blank">fazer arroz</a> a até uma <a href="http://www.google.com.br/search?hl=pt-BR&amp;client=firefox-a&amp;rls=org.mozilla%3Apt-BR%3Aofficial&amp;hs=yp9&amp;q=como+funciona+bomba+nuclear&amp;btnG=Pesquisar&amp;meta=" target="_blank">bomba nuclear</a>. Mas como adquirir conhecimento na nossa área? Como programar melhor? Como otimizar o seu tempo de desenvolvimento? Muitas dessas respostas estão a disposição de todos os programadores desde o inicio do ano 2000, numa das melhores -senão a melhor &#8211; compilações de boas práticas para a área de desenvolvimento de software.</p>
<p>Trata-se do livro <a href="http://www.pragprog.com/titles/tpp/the-pragmatic-programmer" target="_blank">The Pragmatic Programmer, From Journeyman to Master</a>, de <a href="http://en.wikipedia.org/wiki/Andy_Hunt_%28author%29" target="_blank">Andrew Hunt</a> e <a href="http://en.wikipedia.org/wiki/Dave_Thomas_%28programmer%29" target="_blank">David Thomas</a>. Eu já li o livro pelo menos umas duas vezes (falando nisso, preciso entregar o livro ao <a href="http://blog.diogosantos.com/2008/07/the-pragmatic-programmer/" target="_blank">dono</a>!) e recomendo a quem não leu ainda, seja ele junior ou sênior.</p>
<p>O livro traz uma série de dicas sobre como se tornar um bom programador. Segue um pequeno resumo.</p>
<ol>
<li>Preocupe-se em fazer um código bom</li>
<li>Pense!! Critique o seu trabalho</li>
<li>Dê opções, não dê desculpas.</li>
<li>Conserte falhas ao encontrar a falha</li>
<li>Seja um catalizador de mudanças</li>
<li>Lembre-se o &#8216;porquê&#8217; do projeto</li>
<li>Faça da qualidade um requerimento</li>
<li>Invista regularmente no seu portifólio de conhecimento</li>
<li>Analise e critique o que você ouve e vê</li>
<li>É o que você fala e COMO você fala</li>
<li>DRY &#8211; Don&#8217;t Repeat Yourself</li>
<li>Faça facil para ser reutilizavel</li>
<li>Elimine efeitos entre coisas não relacionadas</li>
<li>Não existem decisões finais</li>
<li>Use traçantes para achar o alvo</li>
<li>Prototipar para aprender</li>
<li>Programe para o problema do domínio usando a linguagem do domínio</li>
<li>Estime para evitar supresas</li>
<li>Itere o cronograma com o código</li>
<li>Deixe o conhecimento em arquivos textos</li>
<li>Use o poder das linhas de comando</li>
<li>Use BEM apenas um editor</li>
<li>Sempre use um controlador de versão</li>
<li>Resolva o problema, não a culpa</li>
<li>Não entre em pânico ao debugar</li>
<li>O problema normalmente não é no &#8217;select&#8217;</li>
<li>Não assuma algo, prove!</li>
<li>Aprenda uma linguagem de manipulação de texto</li>
<li>Excreva código que escreva código</li>
<li>Não, você não pode escrever softwares perfeitos. Proteja o seu código.</li>
<li>Desenhe soluções baseadas em contratos</li>
<li>Pegue os problemas precocemente. Teste desde o inicio.</li>
<li>Use asserções para prevenir o impossivel</li>
<li>Use exceções apenas para o excepcional</li>
<li>Termine o que começou</li>
<li>Minimize acoplamentos entre módulos</li>
<li>Configure! Não integre!</li>
<li>Coloque abstração no código e detalhe no metadata</li>
<li>Analise o workflow para melhorar a concorrências</li>
<li>Desenhe usando serviços</li>
<li>Sempre desenhe pensando em concorrência</li>
<li>Separe a visão do modelo</li>
<li>Desenhe e conheça o fluxo da informação</li>
<li>Não programe por concidência</li>
<li>Estime a complexidade dos seus códigos</li>
<li>Teste as suas estimações em unidades reais</li>
<li>Refatore frequentemente, agora e sempre!</li>
<li>Desenvolva para os testes</li>
<li>Teste o seu software, ou os usuários testarão</li>
<li>Não use geradores de código que você não entenda o que foi gerado</li>
<li>Não apenas leia os requisitos. Mergulhe neles. Escave eles!</li>
<li>Trabalhe com um usuário para pensar como um usuário</li>
<li>Abstrações sobrevivem mais do que os detalhes</li>
<li>Crie um glossário de projeto</li>
<li>Ache, pense e pese as &#8216;necessidades&#8217;</li>
<li>Comece quando estiver pronto!</li>
<li>Algumas coisas são melhores prontas do que descritas</li>
<li>Não seja escravo da formalidade</li>
<li>Ferramentas caras não produzem as melhores arquiteturas</li>
<li>Organize o time por funcionalidades, e não por funções.</li>
<li>Automatize o que puder ser automatizado.</li>
<li>Teste frequentemente e automaticamente</li>
<li>Só está pronto quando o teste roda com sucesso</li>
<li>Use sabotadores para testar o seu teste</li>
<li>Não teste apenas o código. Teste as situações do domínio</li>
<li>Ache erros apenas uma vez</li>
<li>Escreva documentos com os mesmos princípios que vc escreve código</li>
<li>Não separe tanto a documentação do código</li>
<li>Exceda a espectativa do seu cliente</li>
<li>Assine o seu trabalho</li>
</ol>
<p>PS: Qualquer duvida, só comentar que eu detalho os itens.</p>
<p>Comente e Recomende!!</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.rodrigoallemand.com.br/?feed=rss2&amp;p=163</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Parabéns a todos! Nós merecemos!!</title>
		<link>http://blog.rodrigoallemand.com.br/?p=156</link>
		<comments>http://blog.rodrigoallemand.com.br/?p=156#comments</comments>
		<pubDate>Tue, 14 Jul 2009 22:17:41 +0000</pubDate>
		<dc:creator>Rodrigo Allemand</dc:creator>
				<category><![CDATA[INCA]]></category>
		<category><![CDATA[Equipe]]></category>
		<category><![CDATA[Liderança]]></category>

		<guid isPermaLink="false">http://blog.rodrigoallemand.com.br/?p=156</guid>
		<description><![CDATA[Ainda não decidi se é com felicidade ou não que eu escrevo este post.
Felicidade de ver todo um trabalho ganhar repercussão nacional, aparecendo numa mídia de alto nível e o melhor, falando muito bem!
Por outro lado, mais uma vez, quem realmente fez isso acontecer, não apareceu&#8230;
Não tirando os méritos dos lideres, que existem, mas acho [...]]]></description>
			<content:encoded><![CDATA[<p>Ainda não decidi se é com felicidade ou não que eu escrevo este post.</p>
<p>Felicidade de ver todo um trabalho ganhar repercussão nacional, aparecendo numa mídia de alto nível e o melhor, falando muito bem!<br />
Por outro lado, mais uma vez, quem realmente fez isso acontecer, não apareceu&#8230;<br />
Não tirando os méritos dos lideres, que existem, mas acho que ao menos um <strong>&#8220;graças aos nossos colaboradores&#8221;</strong> nós mereciamos. Mas faz parte. Uns fazem, outros aparecem.</p>
<p>Estou falando <a title="MAtéria O Globo" href="http://oglobo.globo.com/tecnologia/mat/2009/07/13/projetos-para-inca-se-valem-dos-computadores-da-internet-dos-celulares-para-entender-combater-melhor-cancer-756790518.asp" target="_blank">dessa matéria do jornal O Globo</a>, do caderno de tecnologia (não se tem que estar cadastrado, mas é free).</p>
<blockquote><p>Quatro projetos envolvendo alta tecnologia no combate e no controle do câncer estão em andamento no Rio e no Brasil. E, ao contrário do que possa parecer, trata-se de projetos de âmbito público, não privado, todos a cargo da Fundação do Câncer, que desenvolve as iniciativas para apoiar o Inca (Instituto Nacional de Câncer), hospital de referência na área, na Praça da Cruz Vermelha.</p></blockquote>
<p>Além da simpatia da equipe, trabalhar no INCA tem um apelo que pouquissimas empresas pode trazer, que é a parte social dos produtos finais. Afinal, não estamos aqui para trazer mais clientes, pelo contrário, quanto menos melhor! Não queremos ganhar dinheiro com os produtos, pelo contrário, todas as ferramentas são para um fim privado, que indiretamente gera um valor agregado muito grande para o INCA.</p>
<p>Não é como trabalhar <a href="http://oglobo.globo.com/blogs/tecnologia/" target="_blank">aqui</a> ou <a href="http://www.thoughtworks.com/work-for-us/" target="_blank">ali</a>, onde tudo o que é desenvolvido e criado é visando dinheiro, lucro, clientes, posições, alianças, opniões, etc. Se você pensar no resultado do produto, no fundo, estamos ajudando a muitas pessoas!</p>
<p>Portanto, gostaria de agradecer a todos os que trabalharam nestes projetos que me orgulho de ter, de alguma forma, ajudado a construir.</p>
<p><strong>Projeto QID &#8211; Qualidade da Interpretação Diagnostica</strong></p>
<blockquote><p>O primeiro projeto é o desenvolvimento de um sistema para unificar as informações sobre os exames &#8211; e consequentemente diagnósticos &#8211; do câncer de mama no país.</p></blockquote>
<p><strong>Elizabeth Ribeiro da Silva<br />
Evandro Ribeiro Gomes</strong></p>
<p><strong>Projeto BPW &#8211; Base de Registro Populacional de Câncer</strong></p>
<blockquote><p>Outra frente em que a tecnologia ajudará é uma espécie de &#8220;censo&#8221; da incidência de diferentes tipos de câncer na população brasileira.</p></blockquote>
<p><strong>Pedro Paulo dos Santos<br />
Elaine Cristina Soares Nunes<br />
Tiago Ribeiro de Azevedo<br />
André Luiz Guedes</strong></p>
<p><strong>Projeto RBTMO &#8211; Registro Brasileiro de Transplante de Medula Óssea</strong></p>
<blockquote><p>O terceiro projeto envolvendo tecnologia e câncer diz respeito a transplantes de medula.</p></blockquote>
<p><strong>Shiela de Oliveira Prado<br />
Filipe André Paes Souza</strong></p>
<p><strong>Projeto AD &#8211; Assistência Domiciliar</strong></p>
<blockquote><p>Finalmente, o quarto projeto usa a tecnologia dos telefones celulares para uma missão nobre: dar mais conforto a pacientes em estado terminal.</p></blockquote>
<p><strong>Anderson Ambrósio<br />
Wagner Shimatai</strong></p>
<p style="text-align: center;"><strong>Parabés a todos pela conquista!!!</strong></p>
]]></content:encoded>
			<wfw:commentRss>http://blog.rodrigoallemand.com.br/?feed=rss2&amp;p=156</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Revisão de Código x Programação em Par</title>
		<link>http://blog.rodrigoallemand.com.br/?p=152</link>
		<comments>http://blog.rodrigoallemand.com.br/?p=152#comments</comments>
		<pubDate>Fri, 08 May 2009 13:53:49 +0000</pubDate>
		<dc:creator>Rodrigo Allemand</dc:creator>
				<category><![CDATA[Matodologia Agil]]></category>
		<category><![CDATA[Pair Programming]]></category>
		<category><![CDATA[Programação em Par]]></category>
		<category><![CDATA[Revisão de Código]]></category>
		<category><![CDATA[XP]]></category>

		<guid isPermaLink="false">http://blog.rodrigoallemand.com.br/?p=152</guid>
		<description><![CDATA[Em um ciclo de desenvolvimento em cascata, existe um processo chamado Revisão de Código (Code Review), onde uma pessoa avalia o trabalho de outra pessoa em busca de qualidade, etc. Nas metodologias ageis, esse processo foi substituito por uma ação mais inteligente, que é a Programação em par.
Revisão de código
Sempre me perguntei:
&#8220;Como vou deixar claro [...]]]></description>
			<content:encoded><![CDATA[<p>Em um <a href="http://pt.wikipedia.org/wiki/Processo_de_desenvolvimento_de_software">ciclo de desenvolvimento</a> em <a href="http://pt.wikipedia.org/wiki/Modelo_em_cascata">cascata</a>, existe um processo chamado Revisão de Código (<a href="http://en.wikipedia.org/wiki/Code_review">Code Review</a>), onde uma pessoa avalia o trabalho de outra pessoa em busca de qualidade, etc. Nas metodologias ageis, esse processo foi substituito por uma ação mais inteligente, que é a <a href="http://en.wikipedia.org/wiki/Pair_programming">Programação em par</a>.</p>
<p><strong>Revisão de código</strong></p>
<p>Sempre me perguntei:</p>
<blockquote><p>&#8220;Como vou deixar claro pra uma pessoa no futuro que o que eu pensei foi asssim, e não assado sem usar somente a documentação?&#8221;.</p></blockquote>
<p>Normalmente, em equipes heterogêneas no carater de senioridade, as solições podem pensar bastante diferente, fazendo com que só a documentação não seja suficiente. E esse cenário de equipes heterogêneas é o mais comum em ambientes de <a href="http://www.guj.com.br/posts/list/45/97969.java">fabricas</a>, onde se misturam plenos &#8211; chamados de seniors &#8211; com estagiários &#8211; chamados de juniors. Então, por ser um processo requerido &#8211; por exemplo no <a href="http://pt.wikipedia.org/wiki/CMMI">CMMi</a> &#8211; um pleno desenvolve e um estagiário revisa.</p>
<p><strong>Caso Veridico</strong></p>
<p>Esse lance de revisão me lembra um caso acontecido com um grande amigo meu.</p>
<p>Lá no inicio de vida, a &#8216;tia&#8217; avisa que fará o ditado do emprego de L e do U, mas que haverá uma surpresa na correção, que será feita pelo coleguinha ao lado. Pois bem, começou o ditado e André foi escrevendo:</p>
<ol>
<li>Salto</li>
<li>Alto</li>
<li>Saudade</li>
<li>&#8230;</li>
</ol>
<p>Ao fim, a professora pede pra trocar com o coleguinha ao lado e André troca com o seu amiguinho <em>Filipe</em> (nome fictício). Ao começar a ver o ditado, André percebe que Filipe inverteu todos os empregos de U x L, colocando Sauto, Auto, Saldade, etc. Com isso, André começou a dar errado em cada item do ditado, fazendo com que Filipe ficasse com zero. André entrega a prova a Filipe e recebe a sua. Ao ver o seu ditado, André fica indignado! Filipe corrigiu tudo como escreveu (Sauto, Auto, Saldade) dando zero para André tambem! (É mais engraçado ele contando&#8230;)</p>
<blockquote><p>Conclusão: Pessoas de niveis diferentes não conseguem estabelecer um nivel de revisão satisfatório.</p></blockquote>
<p><strong>Programação em Par</strong></p>
<p>Já na programação em par (Pair Programming) as duas pessoas estão no mesmo momento desenvolvendo o código, fazendo com que a conversa, as duvidas e as soluções faça o código sair da melhor maneira possivel para as duas pessoas, evitando retrabalho.</p>
<blockquote><p>Moral da História: se fosse um ditado em par, de repente, Filipe aprenderia mais rapido e as notas seriam melhores na turma toda.</p></blockquote>
<p>Obs.: <a href="http://www.infoq.com/br/news/2009/01/Pair-Programming-Code-Review">Um ótimo post da InfoQ-Br</a>.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.rodrigoallemand.com.br/?feed=rss2&amp;p=152</wfw:commentRss>
		<slash:comments>3</slash:comments>
		</item>
		<item>
		<title>DDD &#8211; Blindando o Domínio</title>
		<link>http://blog.rodrigoallemand.com.br/?p=141</link>
		<comments>http://blog.rodrigoallemand.com.br/?p=141#comments</comments>
		<pubDate>Thu, 05 Mar 2009 19:11:57 +0000</pubDate>
		<dc:creator>Rodrigo Allemand</dc:creator>
				<category><![CDATA[DDD]]></category>
		<category><![CDATA[Contrato]]></category>
		<category><![CDATA[Design by Contract]]></category>
		<category><![CDATA[Especificação]]></category>
		<category><![CDATA[Facade]]></category>
		<category><![CDATA[Fachada]]></category>
		<category><![CDATA[Pós-condição]]></category>
		<category><![CDATA[Pré-condição]]></category>
		<category><![CDATA[Specification]]></category>
		<category><![CDATA[Validação]]></category>

		<guid isPermaLink="false">http://blog.rodrigoallemand.com.br/?p=141</guid>
		<description><![CDATA[Lembram que nesse post eu falei que o domínio deveria ser fechado e bem definido? Então! A melhor maneira de fazer isso é criar uma camada que faça uma &#8220;blindagem&#8221; no domínio, definindo o acesso a ela e validando contratos para os métodos.
Contrato nada mais é do que vc garantir que o que entra no [...]]]></description>
			<content:encoded><![CDATA[<p>Lembram que <a href="http://blog.rodrigoallemand.com.br/?p=120" target="_blank">nesse post</a> eu falei que o domínio deveria ser fechado e bem definido? Então! A melhor maneira de fazer isso é criar uma camada que faça uma &#8220;blindagem&#8221; no domínio, definindo o acesso a ela e validando <strong>contratos</strong> para os métodos.</p>
<p><a href="http://archive.eiffel.com/doc/manuals/technology/contract/page.html" target="_blank"><strong>Contrato</strong></a> nada mais é do que vc garantir que o que entra no domínio está valido e o que sai está de acordo com o que o método se propõe a fazer! Retirado do <a href="http://www.fragmental.com.br/wiki/index.php/Contratos_Nulos" target="_blank">Wiki do Phillip</a>&#8230;</p>
<blockquote><p>Se quem chamar me garantir a <strong>pré-condição</strong>, eu garanto a <strong>pós-condição</strong>.</p></blockquote>
<p><strong>Garantir a pré-condição</strong> é garantir que todos os parâmetros que vc precisa (e recebe) para efetuar uma ação estejam de acordo com uma especificação mínima. Com isso, a <strong>pós-condição</strong> &#8211; que é a sua resposta do método (retorno) &#8211; estará garantida.</p>
<p>O padrão utilizado neste caso &#8211; para criar uma camada de comunicação do domínio com o mundo &#8211; é o <a href="http://en.wikipedia.org/wiki/Facade_Pattern">Facade</a> (leia-se &#8220;Fasseide&#8221;, &#8220;conjuncão de Face + ade&#8221;), um padrão de projeto citado no livro <a href="http://en.wikipedia.org/wiki/Design_Patterns_(book)">Design Patterns: Elements of Reusable Object-Oriented Softwares</a>, da Gang of Four [Gof]. Ele cita o seguinte:</p>
<blockquote><p>Fornece uma interface unificada para um conjunto de interfaces em um subsistema. Façade define uma interface de nivel mais alto que torna o subsistema mais facil de ser usado.</p></blockquote>
<p>A motivação básica desse padrão é dividir sistemas em subsistemas para reduzir a complexidade do código.</p>
<p>Como eu <a href="http://blog.rodrigoallemand.com.br/?p=129">falei anteriormente</a>, um padrão pode ser desenvolvido de diversas maneiras, mas algumas implementações são tão simples que são frequentemente copiadas ao longo dos projetos. A implementação mais comum de Facade é ter um construtor privado &#8211; para impossibilitar a criação de uma instancia da classe -  e colocar os métodos da facade como estáticos. Veja o exemplo:</p>
<pre name="code" class="java">public class Facade {

    private Facade(){
    }

    public static String sayHello(){
        return "Hello World!";
    }
}</pre>
<p>Dentro do seu método, vc pode perfeitamente trabalhar da maneira que melhor imaginar, porem, <span style="text-decoration: underline;">não convem colocar nenhuma regra de negócio ou validação dentro da facade</span>, já que um método interno do domínio pode referenciar outro método do domínio sem necessariamente passar pela facade.</p>
<p>Existem tambem quem utilize uma classe para fachada, criando outras classes mais especificas para controlar cada ação, dividindo o sistema em sub-dominios, chamados por uma mesma fachada.</p>
<p>Blindar e validar sem ter regra de negócio? Para organizar melhor esta bagunça, Martin Fowler e Erick Evans desenvolveram o padrão <a href="http://en.wikipedia.org/wiki/Specification_pattern">Specification</a>.</p>
<blockquote><p>[...] business logic can be recombined by chaining the business logic together using boolean logic.</p></blockquote>
<p><em>OBS.: <a href="http://martinfowler.com/apsupp/spec.pdf">Aqui está</a> o PDF de Fowler sobre Specification.</em></p>
<p>Com a Specification, vc pode validar, selecionar e até mesmo construir objetos-modelo para satisfazer a sua regra de negócio. Mais uma vez, nenhum padrão tem uma implamentação fixa, todas podem variar, mas a mais utilizada para Specification em Java é a seguinte:</p>
<pre name="code" class="java">public interface Specification&lt;T&gt; {
    boolean isSatisfiedBy(T t);
}</pre>
<p>No exemplo acima, ela retorna true ou false, caso o objeto passado esteja de acordo com a especificação. Esta especificação ainda pode ser de vários tipos, conforme alguns exemplos descrito abaixo:</p>
<pre name="code" class="java">public abstract class AndSpecification&lt;T&gt; implements Specification&lt;T&gt;{

    private final Specification&lt;T&gt; one;
    private final Specification&lt;T&gt; other;

    //Retorna true se o objeto passar pelas duas especificações
    public AndSpecification(Specification&lt;T&gt; one, Specification&lt;T&gt; other) {
        this.one = one;
        this.other = other;
    }

    public boolean isSatisfiedBy(T t){
        return one.isSatisfiedBy(t) &amp;&amp; other.isSatisfiedBy(t);
    }
}</pre>
<pre name="code" class="java">public abstract class OrSpecification&lt;T&gt; implements Specification&lt;T&gt;{

    private final Specification&lt;T&gt; one;
    private final Specification&lt;T&gt; other;

    //Retorna true se o objeto passar por uma das duas especificações
    public OrSpecification(Specification&lt;T&gt; one, Specification&lt;T&gt; other) {
        this.one = one;
        this.other = other;
    }

    public boolean isSatisfiedBy(T t){
        return one.isSatisfiedBy(t) || other.isSatisfiedBy(t);
    }
}</pre>
<pre name="code" class="java">public interface SelectionSpecification&lt;T&gt; {
    //Filtra uma lista de acordo com uma especificação
    List&lt;T&gt; isSatisfiedBy(List&lt;T&gt; list);
}</pre>
<p>Utilizando o <a href="http://blog.rodrigoallemand.com.br/?p=109" target="_blank">nosso exemplo</a>, vamos criar um exemplo para validar o cadastro de um usuário:</p>
<pre name="code" class="java">public class CadastrarUsuarioSpecification
    implements Specification&lt;Usuario&gt; {

    public boolean isSatisfiedBy(Usuario usuario) {
        if(usuario.getNome().equals("") ||
           usuario.getSenha().equals("") ||
           usuario.getLogin().equals("")){
            return false;
        }
        return true;
    }
}</pre>
<p><em>OBS.: Lembrando que isso é apenas um exemplo didático, a entidade usuário do exemplo tem mais campos para serem validados!</em></p>
<p><strong>O Dominio deve ter a sua validação independente do que vc utilize fora dele, seja Client-side com JavaScript ou Server-Side no seu servlet, por exemplo. Sempre faça o Design By Contract valer no seu domínio. </strong></p>
<p>A especificação <em>CadastrarUsuarioSpecification</em> deve executar todas as validações necessárias para a inclusão de um usuário na base de dados. Utilizando-a em conjuntio com a Facade, teriamos algo como:</p>
<pre name="code" class="java">public class Facade {

    private Facade(){
    }

    public static void cadastrar(Usuario usuario){
        CadastrarUsuarioSpecification spec =
            new CadastrarUsuarioSpecification();
        if(spec.isSatisfiedBy(usuario)){
            //Cadastrar usuario
        } else {
            //Levantar erro!
        }
    }
}</pre>
<p>Com isso, isolamos o domínio, garantimos o contrato e o seu domínio está vacinado conta possiveis erros vindo de outras camadas!</p>
<p>P.S.: Para o conceito de Specification não ficar vago, ainda existem muitos modelos de se contruir uma especificação, seja ela para acesso a banco, para colecionar critérios, para gerar um SQL, para filtrar uma lista, etc. O que precisamos ter em mente é que sempre que vc quizer implementar uma regra de maneira clara, procure ver antes se ela se encaixa em uma specification.</p>
<p>Até!</p>
<p>comente e Recomende!</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.rodrigoallemand.com.br/?feed=rss2&amp;p=141</wfw:commentRss>
		<slash:comments>11</slash:comments>
		</item>
		<item>
		<title>DDD &#8211; Entidades e afins</title>
		<link>http://blog.rodrigoallemand.com.br/?p=138</link>
		<comments>http://blog.rodrigoallemand.com.br/?p=138#comments</comments>
		<pubDate>Tue, 03 Mar 2009 18:01:25 +0000</pubDate>
		<dc:creator>Rodrigo Allemand</dc:creator>
				<category><![CDATA[DDD]]></category>
		<category><![CDATA[Desenvolvimento]]></category>
		<category><![CDATA[Data Transfer Object]]></category>
		<category><![CDATA[DTO]]></category>
		<category><![CDATA[Entidade]]></category>
		<category><![CDATA[Entity]]></category>
		<category><![CDATA[JavaBean]]></category>
		<category><![CDATA[Plain Old Java Object]]></category>
		<category><![CDATA[POJO]]></category>
		<category><![CDATA[TO]]></category>
		<category><![CDATA[Transfer Object]]></category>
		<category><![CDATA[Value Object]]></category>
		<category><![CDATA[VO]]></category>

		<guid isPermaLink="false">http://blog.rodrigoallemand.com.br/?p=138</guid>
		<description><![CDATA[A peça chave do DDD é a Entidade (Entity).
Entidade é um objeto com um significado para o domínio sendo modelado e que possui uma identidade.
No exemplo dado no decorrer da série de post, basicamente, estas seriam as nossas entidades. Repare que todas as classes possuem uma identidade (o campo ID de cada classe). Isso define [...]]]></description>
			<content:encoded><![CDATA[<p>A peça chave do DDD é a Entidade (Entity).</p>
<p><strong>Entidade é um objeto com um significado para o domínio sendo modelado e que </strong><strong><span style="text-decoration: underline;">possui uma identidade</span>.</strong></p>
<div id="attachment_111" class="wp-caption aligncenter" style="width: 310px"><a href="http://blog.rodrigoallemand.com.br/wp-content/uploads/2009/02/ddd_diag_classe.gif"><img class="size-medium wp-image-111" title="Diagrama de Classe extraido do Modelo" src="http://blog.rodrigoallemand.com.br/wp-content/uploads/2009/02/ddd_diag_classe-300x266.gif" alt="Diagrama de Classe extraido do Modelo" width="300" height="266" /></a><p class="wp-caption-text">Diagrama de Classe extraido do Modelo</p></div>
<p>No exemplo dado no decorrer da série de post, basicamente, estas seriam as nossas entidades. Repare que todas as classes possuem uma identidade (o campo ID de cada classe). Isso define uma Entidade: a sua identificação única!</p>
<div id="attachment_112" class="wp-caption aligncenter" style="width: 310px"><a href="http://blog.rodrigoallemand.com.br/wp-content/uploads/2009/02/mer_ddd.gif"><img class="size-medium wp-image-112" title="Modelo de dados extraido do Diagrama de Classes" src="http://blog.rodrigoallemand.com.br/wp-content/uploads/2009/02/mer_ddd-300x228.gif" alt="Modelo de dados extraido do Diagrama de Classes" width="300" height="228" /></a><p class="wp-caption-text">Modelo de dados extraido do Diagrama de Classes</p></div>
<p>Pensando em um modelo relacional, basicamente, cada entidade representa um registro de uma tabela e as suas referências e dependências. Mas preste a atenção: <span style="text-decoration: underline;">um modelo relacional é diferente de um modelo de entidades</span>, já que existem diferenças em cada mundo. Veja, por exemplo, a tabela Workflow: não existe referencia a ela como uma classe, mas existe uma coleção, dentro da entidade de Status que referencia esta associação.</p>
<p><strong>DTO x TO x VO x Entidade x Pojo x JavaBean</strong></p>
<p>Vc já ouviu falar de <strong>DTO</strong> (Data Transfer Object), correto?<br />
E de <strong>TO</strong> (Transfer Object)?<br />
E de <strong>VO</strong> (Value Object)?<br />
E de <strong>POJO</strong> (Plain Old Java Object)?<br />
E de <strong>Java Bean</strong>?</p>
<p>Se vc acha que é tudo a mesma coisa, vc está enganado!</p>
<p><a href="http://java.sun.com/blueprints/corej2eepatterns/Patterns/TransferObject.html">TO</a> foi citado pelo grupo Core J2EE Patterns inicialmente e foi desenhado para ser usado quando aplicações precdisam se comunicar com EJBs, reduzindo a quantidade de métodos a serem chamados.</p>
<p><a href="http://martinfowler.com/eaaCatalog/dataTransferObject.html">DTO</a> segue um proncípio parecido, só não cita EJB e foi descrito por Martin Fowler.</p>
<p>Básicamente, TO e DTO são a mesma coisa, um monte de campos com um bando de métodos acessores (Get e Set) para trafegar informação entre dois &#8220;extremos&#8221;.</p>
<p>Fowler ainda vai adiante e escreve:</p>
<blockquote><p><span class="postbody"><span style="text-decoration: underline;">Data Transfer Object is one of those objects our mothers told us never to write.</span> It&#8217;s often little more than a bunch of fields and the getters and setters for them. The value of this usually hateful beast is that it<br />
result you need to reduce the number of calls, and that means that you need to transfer more data with each d to procall. One way to do this is to use lots of parameters. However, this is often awkwaronly a single value.often impossible with languages such as Java that return The solution Mels How It Works In many ways, amore than a bun<br />
allows you to move several pieces of information over a network in a single call?a trick that&#8217;s essential for<br />
tributed systems. </span></p></blockquote>
<p>Já o padrão <a href="http://martinfowler.com/eaaCatalog/valueObject.html">VO</a> é como se fosse um <strong>DTO imutável</strong>, ou seja um objeto que mantem o seu valor no decorrer da sua vida. O número 5 sempre vai ser 5. Quando vc muda o 5 pra 6, ele deixa de ser o número 5 e vira o numero 6. Número neste caso é um objeto de valor, um é diferente do outro. Em Java, String, Date, todos os Number. Normalmente</p>
<p>Fowler define Value Object como:</p>
<blockquote><p>A small simple object, like money or a date range, whose equality isn&#8217;t based on identity.</p></blockquote>
<p>VO não tem identidade, tem valor!</p>
<p>Já o <a href="http://www.martinfowler.com/bliki/POJO.html">POJO</a>, cunhado por Martin Fowler e cia, são <a href="http://en.wikipedia.org/wiki/POJO">objetos simples</a>. São aqueles objetos que não enxtendem ou implementan ninguem. Não dependem de nenhuma atividade externa. São objetos simples que utilizam somente códigos &#8220;nativos de Java&#8221;.</p>
<p>E <a href="http://pt.wikipedia.org/wiki/JavaBeans">Java Bean</a>? Bem, Java Bean é uma <span style="text-decoration: underline;">especificação</span>! É ela que diz que as classes devem começar com letra maiúscula, os métodos em minúscula, os getX, setX e isX da vida..</p>
<p>Resumindo:</p>
<ul>
<li> Pojo são simples objetos puramente Java;</li>
<li>JavaBean é uma especificação;</li>
<li>DTO = TO = Objeto pra transferência de informação;</li>
<li>VO é um DTO que mantem o seu estado</li>
<li>Entidade é um objeto que tem uma identidade em um domínio.</li>
</ul>
<p>Até!</p>
<p>Comente e Recomende!</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.rodrigoallemand.com.br/?feed=rss2&amp;p=138</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>Padrões de Projeto e Expressividade de Código</title>
		<link>http://blog.rodrigoallemand.com.br/?p=129</link>
		<comments>http://blog.rodrigoallemand.com.br/?p=129#comments</comments>
		<pubDate>Mon, 02 Mar 2009 18:39:45 +0000</pubDate>
		<dc:creator>Rodrigo Allemand</dc:creator>
				<category><![CDATA[Desenvolvimento]]></category>
		<category><![CDATA[Anti-Patterns]]></category>
		<category><![CDATA[Design Patterns]]></category>
		<category><![CDATA[Expressividade de Código]]></category>
		<category><![CDATA[Padrão de projeto]]></category>
		<category><![CDATA[Singleton]]></category>

		<guid isPermaLink="false">http://blog.rodrigoallemand.com.br/?p=129</guid>
		<description><![CDATA[Quando eu comecei a vida de desenvolvedor, a minha idéia era que o divisor de águas era quem soubesse escrever &#8220;padrões de projeto&#8221;. Eu não estava completamente errado. Onde eu errei? Vamos lá&#8230;
Christopher Alexander, um renomado arquiteto italiano, uma vez citou:
Cadas padrão descreve um problema no nosso ambiente e o núcleo da sua solução, de [...]]]></description>
			<content:encoded><![CDATA[<p>Quando eu comecei a vida de desenvolvedor, a minha idéia era que o divisor de águas era quem soubesse escrever &#8220;padrões de projeto&#8221;. Eu não estava completamente errado. Onde eu errei? Vamos lá&#8230;</p>
<p><a href="http://en.wikipedia.org/wiki/Christopher_Alexander">Christopher Alexander</a>, um renomado arquiteto italiano, uma vez citou:</p>
<blockquote><p>Cadas padrão descreve um problema no nosso ambiente e o núcleo da sua solução, de tal forma que vc possa utilizar usar esta solução mais de um milhão de vezes, sem nunca faze-lo da mesma maneira.</p></blockquote>
<p>Christopher Alexander não construia sistemas. Ele construia prédios, casas e cidades. Mas a citação acima se encaixa perfeitamente na definição de <a href="http://pt.wikipedia.org/wiki/Padr%C3%B5es_de_projeto_de_software">padrão de projeto para construção de sistemas</a>! São <span style="text-decoration: underline;">soluções</span> para um <span style="text-decoration: underline;">problema</span> conhecido! Não adianta saber &#8220;fazer&#8221; um padrão de projeto. Vc precisa identificar o problema e achar a melhor solução para este problema, seja ela conforme o criador do padrão de projeto citou ou como você achar melhor. Basta que a definição do padrão seja seguida na sua implementação. Portanto, não grave como a sua classe deve ser para atender um determinado padrão, grave o que o padrão prega, o que ele se propõe a solucionar e os principios de design do padrão.</p>
<p>Outro grande problema encontrado é quanto a nomeção de classes. Quando se nomeia uma classe, deve-se deixar bem claro (porem sem termos um texto como nome) o que a classe faz e como ela foi idealizada. Não só com comentários, mas com os nomes claros, deixando-os entendíveis a primeira vista.</p>
<p>Essa é outra motivação dos padrões. A nomeação é tão importante como a sua implementação. Não adianta vc definir um padrão extremamente bem se uma pessoa que vai desenvolver utilizando essa classe, não conseguir enchergar o que ela realmente faz.</p>
<p>Imagine que vc está entrando em um projeto agora e ao abrir o seu workspace, se depara com uma Classe chamada ConfiguracaoSingleton. Automaticamente vc saberá que se trata de uma instância única da configuração da aplicação.</p>
<p>Ter <a href="http://blog.fragmental.com.br/2007/12/28/expressividade-no-codigo/">expressividade no seu código</a> <a href="http://unplugged.giggio.net/unplugged/post/Expressividade-do-codigo.aspx">é 80% de um código bem feito</a>! Se alguem entende o que vc se propoz a fazer, as possiveis correções e manutenções (ou até mesmo, usar o seu código como exemplo) fica muito mais facil.</p>
<p>Portanto nomeie bem seu código e saiba o-que-resolve-o-que.</p>
<p><em>Obs: Vale a pena entender o que é um <a href="http://en.wikipedia.org/wiki/Anti-pattern">Anti-pattern</a> tambem!</em></p>
<p>Para exemplificar melhor, vamos descrever um dos padrões <a href="http://www.google.com.br/search?hl=pt-BR&amp;q=singleton&amp;btnG=Pesquisa+Google&amp;meta=">mais conhecidos</a>, <a href="http://www.plugmasters.com.br/sys/materias/893/1/Padr%F5es-de-Projeto:-Singleton">mais</a> e <a href="http://javafree.uol.com.br/wiki/Singleton">mais</a> <a href="http://www.dsc.ufcg.edu.br/~jacques/cursos/map/html/pat/singleton.htm">exemplificados</a> e mais <a href="http://www.guj.com.br/posts/list/57836.java">mal-entendidos</a> da história do desenvolvimento orientado a objeto: o <a href="http://pt.wikipedia.org/wiki/Singleton">Singleton</a>!</p>
<p>O Singleton foi originalmente criado pelo renomado grupo Gang Of Four [GoF], formado por <a href="http://en.wikipedia.org/wiki/Erich_Gamma">Erich Gamma</a>, <a href="http://en.wikipedia.org/wiki/Richard_Helm">Richard Helm</a>, <a href="http://en.wikipedia.org/wiki/Ralph_Johnson">Ralph Johnson</a> e <a href="http://en.wikipedia.org/wiki/John_Vlissides">John Vlissides</a>.  Sua definição é:</p>
<blockquote><p>Garantir que uma classe tenha somente uma instância e fornecer um ponto global de acesso para a mesma.</p></blockquote>
<p>Resumidamente, a motivação do Singleton é ter um ponto de acesso a uma intancia que seja unica para todo o sistema. As aplicações para este patterns são inúmeras: configuração, tratamento de informação compartilhada, parametrização, manter estado de um objeto, manter instancias de outros objetos que sejam statefull, etc. O qua vai guiar como contruir este objeto é a sua necessidade.</p>
<p style="text-align: center;"><strong>ATENÇÃO: Os códigos utilizados nestes exemplos são meramente ilustrativos.</strong></p>
<p>Vamos ao exemplo mais conhecido de todos:</p>
<pre  name="code" class="java">public class Singleton {

    private static Singleton instance = null;

    private Singleton() {
    }

    public Singleton getInstance(){
        if(instance == null)
            instance = new Singleton();
        return instance;
    }

}</pre>
<p>Este sem dúvidas é o código mais conhecido como Singleton. Mas ai começam os problemas&#8230;</p>
<p>Se eu tiver em um sistema muito concorrido, pode acontecer de duas instancias serem criadas ao mesmo tempo. <span style="text-decoration: underline;">Se isso for realmente um problema</span>, refatorando o código poderemos ter algo como:</p>
<pre  name="code" class="java">public class Singleton {

	private static Singleton instance = null;

	private Singleton() {
	}

	public synchronized Singleton getInstance(){
		if(instance == null)
			instance = new Singleton();
		return instance;
	}

}</pre>
<p>Sincronizando o método, podemos garantir que apenas uma chamada será processada a cada momento. Mas isso torna o código muito ruim, já que até mesmo depois da criação, todas as chamadas deverão ser sincronizadas e, conforme dito no problema 1, a sua concorrência é grande, o que implica em muitos acessos e uma baixa performance desse método.</p>
<p><span style="text-decoration: underline;">Se isso for realmente um problema</span>, para solucionar podemos fazer coisas do tipo:</p>
<pre name="code" class="java">public class Singleton {

    private static Singleton instance = null;

    private Singleton() {
    }

    public Singleton getInstance(){
        if(instance == null)
            synchronized (Singleton.class) {
                instance = new Singleton();
            }
        return instance;
    }

}</pre>
<p>Beleza! com isso conseguimos garantir concorrência e performance, correto? Não, não não&#8230; sendo bem purista, ainda há uma possibilidade de haver uma concorrencia na linha 09 do último exemplo. Sim, é possível sim (Calma, são apenas exemplos, rs)! <span style="text-decoration: underline;">Se isso for um problema</span>, refatorando um pouco mais, podemos ter um código assim:</p>
<pre name="code" class="java">public class Singleton {

    private static Singleton instance = null;

    private Singleton() {
    }

    public Singleton getInstance(){
        synchronized (Singleton.class) {
            if(instance == null)
                synchronized (Singleton.class) {
                    instance = new Singleton();
                }
        }
        return instance;
    }

}</pre>
<p>Pronto! Temos um singleton!!!</p>
<p>Mas ainda temos um probleminha&#8230; E se o sistema tiver rolando em <a href="http://pt.wikipedia.org/wiki/Cluster">Cluster</a>?! <span style="text-decoration: underline;">Se vc tiver</span> mais de uma JVM, vão existir mais e uma instância do seu singleton, o que deixa de ser singleton!</p>
<p>Bem, perceberam que a ligação entre problema e solução não diz respeito a como codificar. Eu tenho vários exemplos de Singleton acima e até o momento eu não resolvi o meu problema, que é ter uma instância, <span style="text-decoration: underline;">que suporte concorrência, com performance e em um ambiente distribuido</span>. E eu poderia fazer milhões de implementações diferentes para conseguir chegar ao meu objetivo!</p>
<p>Mas e se eu não me importasse de ter mais de uma instancia no Cluster? E se a minha concorrência fosse muito pequena a ponto de não atrapalhar a minha performance? Isso cabe a você!!! Como eu disse, conhecer o problema e dar a melhor solução possivel!</p>
<p>Existem todos os tipos de pessoas! Existem aqueles que pensam em uma solução, implementam um ou mais padrões sem ao menos conhecer o que está fazendo; como tambem <a href="http://www.phppatterns.com/docs/design/hello_world_in_patterns">existem aqueles que implementam vários padrões de projeto para um simples Hello World</a> <a href="http://www.guj.com.br/posts/list/51902.java">e mesmo assim, a implementação está errada</a>!</p>
<p>Só para termos ideia, vou colocar mais um exemplo de Singleton. Neste eu utilizo o contexto de uma aplicação Web para individualizar a minha instancia.</p>
<pre name="code" class="java">public class Singleton {

    private static final String KEY = "singleton";

    private Singleton() {
    }

    public Singleton getInstance(ServletContext context){
        Object obj = null;
        obj = context.getAttribute(KEY);
        if(obj == null){
            synchronized (Singleton.class) {
                Singleton singleton = new Singleton();
                context.setAttribute(KEY, singleton);
                return singleton;
            }
        }
        return Singleton.class.cast(obj);
    }

}</pre>
<p>Portanto, entender o seu problema, saber qual padrão de projeto aplicar e nomea-lo corretamente é o divisor de aguas.</p>
<p>Até!</p>
<p>Comente e Recomende!</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.rodrigoallemand.com.br/?feed=rss2&amp;p=129</wfw:commentRss>
		<slash:comments>3</slash:comments>
		</item>
		<item>
		<title>Prematurices da vida contemporânea!</title>
		<link>http://blog.rodrigoallemand.com.br/?p=126</link>
		<comments>http://blog.rodrigoallemand.com.br/?p=126#comments</comments>
		<pubDate>Thu, 26 Feb 2009 17:59:13 +0000</pubDate>
		<dc:creator>Rodrigo Allemand</dc:creator>
				<category><![CDATA[Matodologia Agil]]></category>
		<category><![CDATA[Off-Topic]]></category>
		<category><![CDATA[Desabafo]]></category>
		<category><![CDATA[Metodologia Agil]]></category>
		<category><![CDATA[UserStories]]></category>

		<guid isPermaLink="false">http://blog.rodrigoallemand.com.br/?p=126</guid>
		<description><![CDATA[Uma das grandes barreiras para a adoção de uma metodologia ágil de uma equipe pode ser aquela antiga mania de isolar o cliente das adoções tomadas no decorrer do desenvolvimento. Não adianta! Sem o cliente por perto, não temos metodologia ágil que funcione simplesmente porque sem o cliente por perto, a chance de errarmos aumenta [...]]]></description>
			<content:encoded><![CDATA[<p>Uma das grandes barreiras para a adoção de uma metodologia ágil de uma equipe pode ser aquela antiga mania de isolar o cliente das adoções tomadas no decorrer do desenvolvimento. Não adianta! Sem o cliente por perto, não temos metodologia ágil que funcione simplesmente porque sem o cliente por perto, a chance de errarmos aumenta demais! Isso normalmente acontece quando temos aquele otimo tecnico que virou gestor e parou no tempo onde existia as fases de um produto, e não um produto em fases!</p>
<p>Muitas vezes, por mais que um &#8216;analista&#8217; entenda 100% do que o cliente solicitou, ele não sabe o que o software tem que fazer quando for dado por completo. Nem o cliente saberá isso em um Brainstorm, ainda mais se vc colocar aquela bendita <span style="text-decoration: underline;">fase de levantamento</span> no seu <span style="text-decoration: line-through;">cornograma</span> cronograma.</p>
<p>Dividir o produto em <a href="http://www.extremeprogramming.org/rules/userstories.html">UserStories</a> é dar certeza ao cliente e ao desenvolvedor que, apenas aquele pequeno escopo está sendo desenvolvido neste momento (iteração). Ele não precisa se preocupar no momento que lá na frente o produto tem que se comunicar com 50 pontos diferentes. Isso não está no mini-escopo da UserStory a qual o desenvolvedor está focado!</p>
<blockquote><p>User stories also drive 									the creation of the <a href="http://www.extremeprogramming.org/rules/functionaltests.html">acceptance tests.</a> One or more automated acceptance tests 									must be created to verify the user story has been correctly implemented.</p></blockquote>
<p>Para quem não sabe, eu trabalho no Instituto Nacional do Cancer, com uma equipe de 12 pessoas que desenvolve Java (Web e Mobile) para alguns clientes/institutos satélites do governo. Porem, quando eu cheguei aqui, minha tarefa era &#8220;organizar a casa para que os sistemas que estavam em fase final de levantamento tivessem uma melhor performance de entrega&#8221;.</p>
<p>Pois bem, fiz a minha parte! Os softwares estão sendo entregues <span style="text-decoration: underline;">quase como eles descreveram</span>, mesmo com todos os <span style="text-decoration: underline;">problemas encontrados no meio do caminho</span>! Digo isso porque não sei se enquanto eu escrevi esse post, as novas funcionalidades foram aceitas. Mas ainda me sinto muito insatisfeito com o meu próprio serviço, conforme enumero abaixo:</p>
<ol>
<li>Não há <span style="text-decoration: underline;">testes</span> por parte da equipe, nem falo de unitários ou integrados. Não há teste automatizado de maneira alguma!;</li>
<li>Não há a <span style="text-decoration: underline;">presença do cliente</span>. Estamos desenvolvendo no escuro, levando em consideração o que o gerente do projeto acha, o que não será (quse com certeza) o que o cliente final deseja;</li>
<li>Não há uma <span style="text-decoration: underline;">definição fechada</span> do que fazer e como fazer. Até mesmo coisas básicas como layout são alterados dias antes da entrega final de um módulo, mesmo sem o concentimento do cliente;</li>
<li>Não há <span style="text-decoration: underline;">gerencia de configuração</span> alguma. Os ambientes de desenvolvimento, homologação e produção são diferentes a ponto de serem utilizadas versões de softwares e bibliotecas comuns diferentes entre esses ambientes;</li>
<li>Há sempre o &#8220;faz como esse aqui&#8221;. <span style="text-decoration: underline;">Sistemas arcaicos</span> com soluções <span style="text-decoration: underline;">precárias como exemplo</span>&#8230; nesse eu nem preciso me aprofundar muito!</li>
<li>Minha-Própria-Metodologia-Ágil não funciona se todos não tiverem completa noção de como funciona. Para qualquer metodologia funcionar, tudo deve estar entendido e todos devem estar de acordo.</li>
</ol>
<p>Para se ter noção melhor sobre o que eu passo, na proxima terça feira (03/03/2009) deveriamos fazer um deploy contendo 80% do projeto para o cliente. Mas quem vai testar é o gerente do projeto, já que o cliente só vai ver quando o produto estiver 100% pronto. Mas amanhã teremos uma reunião para definir um escopo de versionamento de informações, que é vital para um processo de certificação (escopo do sistema). MAs calmae, amanhã para entregar numa terça?! Sugeri então envolver o cliente, mesmo que por audio conferência, para ter uma solução aprovada por ele, porque a alteração iria ser muito grande. Resposta: Vamos definir entre nós, o cliente será avisado sobre a nossa decisão!!</p>
<p>Um outro exemplo aqui tambem: o sistema ainda não tem usuário final e está em fase de homologação?!? Como assim?!? Quem definiu isso?!?</p>
<p>Enfim, estou muito insatisfeito e tenho plena noção de que não conseguirei alterar isso a curto prazo, ou seja, até a entrega desses produtos aos seus clientes com a etiqueta &#8220;SURPRESA!&#8221; Gosto muito do local, da empresa, da causa (principalmente) e das pessoas. Mas as metodologias e os modelos estão me esgotando!</p>
<p>Mas a minha saga em busca do projeto-agil-piloto-que-transformará-toda-a-empresa continua!</p>
<blockquote><p><em>&#8220;Não é o mais forte que sobrevive, nem o mais inteligente, mas o que melhor se adapta às mudanças&#8221; &#8211; Charles Darwin</em></p></blockquote>
<p>Até!</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.rodrigoallemand.com.br/?feed=rss2&amp;p=126</wfw:commentRss>
		<slash:comments>4</slash:comments>
		</item>
	</channel>
</rss>
