quinta-feira, 12 de dezembro de 2013
Postmon - API para consultar CEP
Nessa apresentação do InfoQ Alê Borba conta a história da criação da API.
Site da API: http://postmon.com.br/
terça-feira, 10 de dezembro de 2013
Templates free para o Bootstrap
Amplamente difundido entre designers e programadores, sua utilização tem sido cada vez mais utilizadas principalmente devido a recursos bem interessantes como recurso de layout reponsive.
Um dos sites mais famosos de vendas de layout, o ThemeForest tem em vários de seus produtos o Bootstrap como base. Mas pra quem não esta afim de gastar em torno U$30,00 (em média) para ter um layout pronto com o Bootstrap, você pode baixar layouts free (bem mais simples) no Start Bootstrap ele tem alguns templates prontos como:
- Shop Homepage: http://startbootstrap.com/shop-homepage;
- Admin: http://startbootstrap.com/sb-admin;
- Blog: http://startbootstrap.com/blog-home;
- E vários outros para Business: http://startbootstrap.com/home-page-templates
segunda-feira, 9 de dezembro de 2013
WCF com Log4Net
Pra quem precisa utilizar o Log4Net com o WCF disponibilizei uma biblioteca bem simples de integração entre os dois:
http://eduardosilva.github.io/Trinity.Wcf.Log4Net/
Endereço do NuGet:
https://www.nuget.org/packages/TrinityWcfLog4Net/
domingo, 23 de dezembro de 2012
ASP.Net MVC: Muito código nas Controllers
Com o ASP.Net Web Forms, por padrão, temos um code behind (*.aspx.cs) por página (*.aspx) isso significa que temos tem uma classe, que podemos de certa forma caracterizar como uma controller, responsável por uma View. Já no ASP.Net MVC podemos ter um Controller responsável por varias views. Ex.: ProdutoController responsável pelas view Pesquisar, Detalhe, Edicao. Nesta mesma controller podemos potencializar a sua aplicação deixando-a responsável por responder chamadas de json.
Bom com isso acabamos tendo muito código nas nossas controllers (consultas, escritas, conversões de tipos etc). E isso não é culpa da tecnologia é apenas uma questão de como organizar as idéias e responsabilidades.
Com essa quantidade de código nas Controller fica dificil de dar manutenção, mesmo refatorando em métodos você acaba vendo um código muito extenso na sua controller o que de cara parece ser um mal sinal (ou um mal cheiro).
Não precisamos "reinventar a roda" para resolver esses problemas, grandes mentes já tem várias sugestões sobre isso e quero apenas apresentar algumas delas que eu estou utilizando e tem me agradado.
CQRS (Command Query Responsibility Segregation) é um padrão que tenho utilizado para organizar esse tipo de coisa, não vou entrar em detalhes sobre o padrão, isso vai ficar para outro post, vou focar apenas em como estou aplicando nos meus projetos.
Consultas
O primeiro problema que eu resolvi foi referente a consultas. Se você utiliza um OR/M como o Entity Framework ou NHibernate com o ASP.Net MVC você pode acabar tendo muito código de consulta dentro da sua controller.
OBS.: Eu não costumo encapsular os frameworks de OR/M com DAOs ou Repositories. Se estiver interessando no motivo leia o artigo abstração da abstração. Só pra reforçar que isso também não é coisa da minha cabeça, Ayende Rahien é um grande defensor da idéia de que abstrair OR/M é um erro.
Eu utilizo para as consultas o Query Object Pattern (link), com isso consigo encapsular as consultas nessas classes. Isso também evita a questão de trazer todas as propriedades das entidades relacionadas na consulta, eu consigo criar consultas espeficidas para fins específicos de uma View, o que traz um grande ganho de performance. (uma coleção de uma determinada entidade para popular um combobox pode te dar muito dor de cabeça. Acredite!).
Escritas
Para as escritas estou utilizando o Command Pattern, com ele eu consigo refatorar o processo de escrita em várias blocos de comando, afinal nem sempre nossas telas só precisamos executar um salvar correto? Como utilizo muito o Entity Framework, também fica fácil seperar esses comandos utilizando uma única instancia de context e controle de transação quando necessário.
Se você pesquisar sobre esse padrão verá outros padrões relacionados como o Tasks e Events, porém os meus projetos até o momento não precisou desse potencial todo.
Basicamente estou organizando os meus projetos da seguinte forma:
- Entities
- Commands
- QueryObjects
- Controllers
- Views
- Models
Até a próxima!
sábado, 13 de agosto de 2011
Extensions Methods e Namespaces
Eu utilizo Extensions Methods para praticamente duas finalidades:
- Implementar uma funcionalidade não existente para um objeto;
- Dar uma maior coesão a um trecho de código;
Como exemplo de coesão, veja o trecho de código abaixo:
Para deixar o código um pouco mais coeso pode implementado da seguinte forma:
Para criar uma classe que implemente o código que queremos é muito simples:
Agora pra utiliza-lo basta fazer o seguinte:
Pois é, o Visual Studio já me avisou que não encontrou o meu método de extensão. Isso se dá por que esqueci de fazer o using para o namespace onde esta a extensão, e isso aconteceu por que o intellisense não me deu essa opção.
Quando criamos um extension method dentro de uma namespace precisamos lembrar de fazer o using manualmente toda vez que queremos utiliza-lo, o que nem sempre é legal.
O que podemos fazer nesse caso?
Duas opções:
- Não definir uma namespace para a sua classe que contém os métodos de extensão;
- Definir o namespace igual ao objeto ao qual o método esta atrelado.
Fica ai a dica, agora é só mandar bala nos extensions methods.
terça-feira, 19 de abril de 2011
O Inferno do Utils, Tools e afins!
Quando estamos pensando nas “camadas” da nossa solução, principalmente no começo do projeto, de uma forma geral temos grandes preocupações com assuntos como por exemplo coesão de responsabilidades, baixos acoplamentos, performance e segurança.
Se você esta em um projeto onde o pessoal diagrama tudo antes de começar a programar, se for criado uma classe diferente do que estava no diagrama os alarmes de incêndio são disparados.
De repente surge uma necessidade de enviar e-mail em mais de um ponto do sistema. Nós como “bons programadores” que somos não vamos duplicar o código, então o que fazemos? Criamos um projeto chamado Utils (tools e seus primos).
Se precisamos encapsular uma transferência de arquivo via ftp agora não temos mais a “dor de cabeça” de decidir onde colocar esse tipo de funcionalidade, muito simples vai para o Utils.
Encapsulamento de leitura e gravação de um xml também não é mais problema, é só colocar no Utils que fica “tudo certo”.
Se pegarmos esse exemplo em particular fica claro que todos os cuidados que estávamos tomando na criação da solução foram totalmente ignorados quando passamos a ter o projeto Utils. E o pior é que fica tendencioso, se aparecer qualquer funcionalidade que não sabemos onde colocar, ela possivelmente irá parar no Utils.
Existem vários problemas com essa abordagem sendo alguns deles:
- O projeto fica dependendo de vários Assemblies, das mais diversas finalidades: E-mail, FTP e acesso a banco são dependências claras no exemplo citado.
- Se você tiver vários projetos que utiliza o seu Utils, cada alteração que você faça no seu Utils, recompila todos os projetos dependentes.
- O projeto vira um “saco de lixo” de código. Lixo mesmo, por que é incrível como a grande maioria das vezes a qualidade do código cai em classes que são colocadas nesses projetos.
Precisa realmente encapsular o envio de e-mail? Precisa mesmo? Será que você não esta sendo motivado em fazer isso simplesmente para facilitar o envio de e-mail? Será que você não esta criando uma abstração da abstração?
Caso seja realmente necessário encapsular o envio de e-mail minha sugestão é que faça isso de verdade, crie uma projeto com essa funcionalidade com um nome sugestivo para o que ele se propõe a fazer. Assim fica claro o que assembly fará, inclusive podemos prever possíveis dependências que isso pode trazer na hora de utilizá-lo.
sexta-feira, 25 de março de 2011
A Abstração da Abstração
O problema é que muitas vezes limitamos a utilização da ferramenta a aquilo que estamos diexando disponível nas nossas classes. O quanto isso vale a pena?
Vou pegar como exemplo os nossos Repositories, geralmente o utilizamos como uma abstração de acesso a dados, e deixamos disponíveis em nossos repositories os famosos métodos Save, GetById, GetAll, etc…
Bom, hoje em dia é muito comum utilizarmos um framework ORM para facilitar as implementações de banco de dados, mas perceba, o ORM é uma abstração de acesso a dados, claro, não igual ao Repository, porém não deixa de ser uma abstração de acesso.
Quando encapsulamos os métodos do ORM nos nossos repositories estamos perdendo poderosas features como por exemplo o Multiquery e e Future do NHbernate.
Não tenho a pretensão de classificar quando isso é bom ou ruim, mas cada caso precisa ser analisado com calma.
Fica ai a bandeira levantada.
Até a próxima.
quinta-feira, 17 de março de 2011
Compilando para Silverlight
Essa dica eu ja mandei para o MUGSP mas resolvi deixar registrado aqui também.
Não sei se alguém algum dia vai precisar disso, mas se estiver tentando gerar um dll com código C# compilado “na mão” para Silverlight, tem que fazer o seguinte:
- Todas as referencias devem ser feitas para as dlls compiladas para Silverlight (System.dll, mscorlib.dll e assim por diante). No meu caso faço referencias as dlls que estão na pasta c:\Arquivos de programas\ReferenceAssemblies\Microsoft\Framework\Silverlight\v4.0\
- Para o compilador (csc.exe) é necessário informar os argumentos /nostdlib+ /noconfig. Isso é necessário para que não seja gerado referencia para as bibliotecas padrões do .Net Framework.
- No caso de utilizar o CodeDom (que foi o meu caso), é necessário passar esses argumentos para CompilerParameters:
new CompilerParameters
{
OutputAssembly = Path.Combine(outputDir, baseNamespace + ".Silverlight.dll"),
CompilerOptions = @"/noconfig /nostdlib"
};
Fica ai a dica pra quem precisar.
Até a próxima.
segunda-feira, 14 de março de 2011
DDD: Melhorando a forma de carregar as Views utilizando Modelo Rico.
DDD sem dúvida é uma excelente ferramenta para auxiliar a resolver problemas que surgem em domínios complexos porém, como todo mundo diz, não é bala de prata. Mas o problema que eu vou expor aqui não é exclusivo de quem utiliza DDD e sim de qualquer solução que se utiliza de Modelo de Domínio Rico.
Quando você tem um Modelo de domínio rico as operações de escrita ficam mais coesas, as responsabilidades ficam mais claras além de outros benefícios, no entando, você pode ganhar alguns problemas nas operações de leitura.
Imagine uma tela onde você tenha três combobox, cada combobox populada com uma entidade diferente. Agora imagine essas entidades com um número significativo de propriedades (não vou definir aqui o quanto seria esse número, essa discussão não vem ao caso agora) e uma cadeia de relacionamento complexa (A relacionada com B que se relaciona com C e assim por diante). Como faríamos para popular esses combos da tela?
Certamente você utilizaria o repositorio especifico para cada uma das entidades e faria a consulta apropriada para popular os combos.
Você conseguiu identificar alguma problema nisso? Não? Então deixa eu ajudar.
Você percebeu quantas chamadas ao banco de dados você teve que fazer? Se você tiver utilizando alguma forma de serviço (WCF, WCF Data Services, ou qualquer outro tipo de serviço) você teve que chamar no mínimo três chamadas de serviço e cada chamada de serviço resultou em uma chamada de banco de dados.
Pronto, ta ai o pretesto que o seu companheiro de trabalho ou o seu gerente de projetos precisava para falar que DDD não presta! Mas esse tipo de problema também tem solução.
Primeira coisa: Pelo amor de Deus, use um ORM. Se você é daqueles programadores que ainda tem resistência a um ORM (como eu tinha) pare com isso agora antes que a coisa fique feia!
Com a utilização de ORM podemos utilizar recursos que nos ajudam na performance da aplicação como Lazy Loading, Cache, operações em Batch. O NHibernate tem funcionalidades excelentes para esses tipos de caso, por exemplo, com o Future poríamos popular os três combobox com uma única chamada para o banco de dados.
Segundo: Popule sua View somente com dados que ela precisa. Se para um combobox só precisamos de um Id e Descrição, pra que vamos trazer todos os dados da entidade? Novamente ferramentas como o NHibernate nos ajudam com esse tipo de situação.
De onde eu tirei essas soluções? CQRS.
Pretendo colocar algumas soluções práticas para esse tipo de situação, mas ja adianto as dicas apresentadas aqui é apenas uma das várias formas que temos para resolver esse problema. O importante é reconhecer que o problema esta lá e ter a mente aberta para as muitas formas de resolve-lo.
Até mais.
sexta-feira, 11 de março de 2011
Silverlight: Dica de performance
Essa semana resolvi um problema interessante de uma aplicação feita em Silverlight.
Estava investigando por que uma determinada aplicação estava lenta e atacamos nas coisas mais óbvias: acesso a banco, chamadas de serviço, tamanho de objetos e por ai vai. Aparentemente não havia que justificasse a lentidadão da aplicação.
Resolvemos então verificar se não havia algum recurso que estavamos usando do silverlight para causar o problema. Procurando no Google por pessoas que passaram pelo mesmo problema, vimos várias dicas referentes ao uso de transparencia e os problemas que isso pode causar quando não utilizado com moderação.
A nossa aplicação não estava utilizando transparencia mas sim sombra (DropShadow), quando removemos o efeito: Bingo!
Não estou querendo dizer que o DropShadow causa problema de performance, tanto que continuamos usando, mas removemos esse efeito em alguns pontos para ter a melhoria necessária sem prejudicar o layout, ou seja, é importante ficar atento ao uso desse tipo de recurso e o quanto ele pode onerar o desempenho da aplicação.
Abraços!