{"id":505,"date":"2017-04-12T10:38:50","date_gmt":"2017-04-12T13:38:50","guid":{"rendered":"http:\/\/gianfratti.com\/?p=505"},"modified":"2017-04-12T18:50:00","modified_gmt":"2017-04-12T21:50:00","slug":"design-patterns-injecao-de-dependencia-com-c","status":"publish","type":"post","link":"http:\/\/gianfratti.com\/index.php\/design-patterns-injecao-de-dependencia-com-c\/","title":{"rendered":"Design Patterns &#8211; Inje\u00e7\u00e3o de Depend\u00eancia com C#"},"content":{"rendered":"<p>Hoje falaremos sobre algo bastante interessante e \u00fatil na \u00e1rea de Desenvolvimento de Sistemas. Vamos falar sobre <a href=\"http:\/\/www.devmedia.com.br\/curso\/design-patterns-com-net\/286\" target=\"_blank\">Design Patterns<\/a>.<\/p>\n<p>Design Patterns ou Padr\u00f5es de Projetos, de um modo geral, consiste numa s\u00e9rie de modelos de resolu\u00e7\u00e3o de problemas recorrentes em projetos de desenvolvimento de softwares.<!--more--><\/p>\n<p>Suas ra\u00edzes se encontram na obra do engenheiro Chistopher Alexander, que redigiu uma s\u00e9rie de textos sobre suas experi\u00eancias em resolu\u00e7\u00e3o de problemas em sua \u00e1rea de atua\u00e7\u00e3o, a Engenharia Civil. Segundo ele, cada Pattern descreve um problema recorrente em projetos, e a partir disso, descreve a solu\u00e7\u00e3o para tal problema de maneira tal, que essa solu\u00e7\u00e3o sirva para outros projetos semelhantes.<\/p>\n<p>Esses princ\u00edpios foram adaptados para a Engenharia de Software e culminou na publica\u00e7\u00e3o da obra \u201cDesign Patterns: Elements of Reusable Object &#8211; Oriented Softwares\u201d em 1995, de autoria de Eric Gamma, Richard Helm, Ralph Johnson e John Vlissides. Ainda hoje esse livro \u00e9 a maior refer\u00eancia no assunto e sem d\u00favida alguma \u00e9 a principal base para a evolu\u00e7\u00e3o dos Patterns. Esta obra descreve 23 Patterns, sendo que com o passar do tempo muitos outros foram documentados e catalogados, por\u00e9m, os 23 Patterns iniciais s\u00e3o ainda os mais utilizados.<\/p>\n<p>Para maiores informa\u00e7\u00f5es visitem esse site que re\u00fane muita documenta\u00e7\u00e3o sobre o assunto : <a href=\"http:\/\/hillside.net\/patterns\/\" target=\"_blank\">http:\/\/hillside.net\/patterns\/<\/a>.<\/p>\n<p>Agora que sabemos o que s\u00e3o e como surgiram os Design Patterns, vamos estudar uma forma de implementa\u00e7\u00e3o de um deles. Vamos ver o padr\u00e3o Dependency Injection ou Inje\u00e7\u00e3o de Depend\u00eancia.<\/p>\n<h3><b>O que \u00e9 Dependency Injection?<\/b><\/h3>\n<p>\u00c8 um dos Patterns catalogados. Em linhas gerais este padr\u00e3o \u00e9 uma das formas de implementar um outro padr\u00e3o &#8211; <b>Invers\u00e3o de Controle<\/b>.<br \/>\nDevemos utilizar esse padr\u00e3o quando temos a necessidade de desenvolver sistemas em que o n\u00edvel de <b>acoplamento <\/b>entre seus diferentes m\u00f3dulos precisem ser extremamente baixos.<br \/>\nPara quem n\u00e3o conhece este termo, <b>acoplamento \u00e9 <\/b>uma conex\u00e3o ou depend\u00eancia ou at\u00e9 mesmo intera\u00e7\u00e3o entre diversos m\u00f3dulos\/sistemas de um projeto de software. Quanto maior for o acoplamento entre os diversos m\u00f3dulos de um sistema, maior a coes\u00e3o deste. Por\u00e9m quanto maior o n\u00edvel de depend\u00eancia dos m\u00f3dulos, mais dif\u00edcil e trabalhosa \u00e9 a manuten\u00e7\u00e3o dos mesmos, pois dar manuten\u00e7\u00e3o em sistemas altamente coesos \u00e9 como tirar uma carta de um castelo de baralhos para dar uma polidinha nela, sem deixar o castelo ruir. E mais, depois de polir a carta, devemos coloc\u00e1-la de volta, sem abalar a estrutura do castelo.<br \/>\nA fun\u00e7\u00e3o principal deste Pattern \u00e9 oferecer uma estrutura de baixo acoplamento, visando os seguintes benef\u00edcios:<\/p>\n<p>A) Oferecer reusabilidade de componentes, uma vez que criamos componentes interdependentes, eles podem ser facilmente implementados em sistemas diversos. B) Facilitar a manuten\u00e7\u00e3o de Sistemas, fazendo com que as manuten\u00e7\u00f5es em m\u00f3dulos n\u00e3o afetem o restante do sistema. C) Criar c\u00f3digos altamente \u201ctest\u00e1veis\u201d. Uma vez que temos c\u00f3digos implementados seguindo esse Pattern, podemos test\u00e1-los mais facilmente utilizando os \u201cmock tests\u201d. D) Criar c\u00f3digos mais leg\u00edveis, o que torna mais f\u00e1cil a compreens\u00e3o do sistema como um todo.<\/p>\n<h3><b>Meios de Implementa\u00e7\u00e3o de Dependency Injection<\/b><\/h3>\n<p>Ao projetar uma aplica\u00e7\u00e3o orientada a objeto, devemos sempre nos preocupar em deixar a aplica\u00e7\u00e3o bastante flex\u00edvel, de modo a facilitar manuten\u00e7\u00f5es e criar novas funcionalidades. Na pr\u00e1tica, isso significa que os objetos que iremos criar na aplica\u00e7\u00e3o devem ter o m\u00ednimo poss\u00edvel de depend\u00eancia. Esses objetos devem ter apenas as depend\u00eancias necess\u00e1rias para realizarem suas tarefas. Todas as depend\u00eancias devem ser minimizadas, e \u00e9 ai que entra o Pattern Dependency Injection. Existem quatro maneiras de implementar Dependency Injection. S\u00e3o elas:<\/p>\n<p>A) <b>Constructor <\/b>=&gt; Modo em que implementamos a inje\u00e7\u00e3o de depend\u00eancia na defini\u00e7\u00e3o dos construtores das classes;<br \/>\nB) <b>Getter and Setter<\/b> =&gt; Modo em que implementamos a inje\u00e7\u00e3o de depend\u00eancia na defini\u00e7\u00e3o dos Gets e Sets das classes;<br \/>\nC) <b>Interface Implementation<\/b> =&gt; Modo em que se usa a defini\u00e7\u00e3o de Interfaces para realizar a inje\u00e7\u00e3o de depend\u00eancia;<br \/>\nD) <b>Service Locator<\/b> =&gt; Modo em que constru\u00edmos classes que servem como \u201clocalizadoras\u201d de objetos que iremos instanciar em nossas outras classes.<\/p>\n<p>Abaixo segue uma ilustra\u00e7\u00e3o que explica como funcionam os conceitos de Inversion of Control (IOC), Dependency Injection (DI) e as quatro maneiras de implementar DI.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" class=\"imagem_artigo\" src=\"http:\/\/gianfratti.com\/wp-content\/uploads\/2017\/04\/DepInj_1.png\" width=\"600\" height=\"235\" border=\"\" \/><\/p>\n<p>Para estudarmos essas quatro metodologias, vamos tomar como exemplo um cen\u00e1rio muito comum em projetos. Vamos pensar em cadastro de empresas. Neste cen\u00e1rio, sempre existe uma classe que ir\u00e1 refletir a entidade Empresa e dentro da classe Empresa muitas vezes encontramos uma refer\u00eancia a outra classe &#8211; Endere\u00e7o, pois uma empresa possui um ou mais endere\u00e7os.<\/p>\n<p>Eis aqui o que geralmente encontramos na classe Empresa:<\/p>\n<div class=\"div_listagem\">\n<pre class=\"brush: php; title: ; notranslate\" title=\"\">\r\n        public class Empresa\r\n        {\r\n            private int _cod;\r\n \r\n            public int Cod\r\n            {\r\n                get { return _cod; }\r\n                set { _cod = value; }\r\n            }\r\n            private string _razaoSocial;\r\n \r\n            public string RazaoSocial\r\n            {\r\n                get { return razaoSocial; }\r\n                set { razaoSocial = value; }\r\n            }\r\n \r\n            private Endereco _endereco;\r\n \r\n            public Endereco Endereco\r\n            {\r\n                get { return _endereco; }\r\n                set { _endereco = value; }\r\n            }\r\n \r\n        }\r\n<\/pre>\n<p>Analisando o c\u00f3digo acima observamos que a classe Empresa possui uma propriedade do tipo Endereco. Neste modelo, utilizamos uma classe concreta para apontar o tipo de nossa propriedade. Isso \u00e9 um exemplo de um alto acoplamento de componentes, pois criamos aqui uma interdepend\u00eancia e uma refer\u00eancia dentro da classe Empresa que pode nos resultar em problemas.<\/p>\n<p>Vamos resolver esse problema de alto grau de acoplamento utilizando Dependency Injection nos seus 4 modos de implementa\u00e7\u00e3o:<\/p>\n<h3><b>Constructor Methodology<\/b><\/h3>\n<p>Nesta metodologia, passamos a refer\u00eancia de objeto no pr\u00f3prio construtor. Deste modo, quando criarmos uma inst\u00e2ncia da classe Empresa, podemos definir o tipo do objeto que queremos para nossa propriedade Endereco.<\/p>\n<p>Veja agora como ficaria o construtor da classe utilizando essa metodologia.<\/p>\n<pre class=\"brush: php; title: ; notranslate\" title=\"\">\r\n        public interface IObjetoEndereco\r\n        {\r\n            #region Declarar Propriedades e M\u00e9todos\r\n            \r\n            #endregion\r\n        }\r\n \r\n        public class Empresa\r\n        {\r\n            private IObjetoEndereco _endereco;\r\n            \r\n            public Empresa(IObjetoEndereco objeto)\r\n            {\r\n                _endereco = objeto;\r\n            }\r\n \r\n        }\r\n<\/pre>\n<p>Note o leitor, que n\u00e3o estamos mais utilizando uma propriedade do tipo Endereco na classe Empresa. N\u00f3s criamos uma <b>Interface <\/b>e agora ela \u00e9 o tipo da propriedade Endereco. Vejam que o construtor da classe, recebe um par\u00e2metro do tipo IObjetoEndereco, e seta a propriedade privada _endereco com o valor deste par\u00e2metro.<\/p>\n<p>Qual a vantagem de utilizar esta metodologia? A resposta \u00e9 muito simples. Deste jeito, deixamos o cliente que est\u00e1 instanciando um objeto Empresa, decidir qual ser\u00e1 o tipo da propriedade Endere\u00e7o. Vamos supor que no primeiro release do sistema, nossa classe Endere\u00e7o seja da seguinte forma:<\/p>\n<pre class=\"brush: php; title: ; notranslate\" title=\"\">\r\n\r\n        public class Endereco : IObjetoEndereco\r\n        {\r\n            private string _logradouro;\r\n            private int _numero;\r\n            public string Logradouro\r\n            {\r\n                get { return _logradouro; }\r\n                set { _logradouro = value; }\r\n            }\r\n \r\n            public int Numero\r\n            {\r\n                get { return _numero; }\r\n                set { _numero = value; }\r\n            }\r\n \r\n        }\r\n<\/pre>\n<p>Nesta situa\u00e7\u00e3o a classe Endere\u00e7o <b>herda <\/b>a Interface IObjetoEndereco e define duas propriedades.<\/p>\n<p>Agora imaginemos que a classe Endere\u00e7o ter\u00e1 mais que duas propriedades, por exemplo:<\/p>\n<pre class=\"brush: php; title: ; notranslate\" title=\"\">\r\n        public class EnderecoPlus : IObjetoEndereco\r\n        {\r\n            private string _tipoLogradouro;\r\n            private string _logradouro;\r\n            private int _numero;\r\n \r\n            public string TipoLogradouro\r\n            {\r\n                get { return _tipoLogradouro; }\r\n                set { _tipoLogradouro = value; }\r\n            }\r\n \r\n            public string Logradouro\r\n            {\r\n                get { return _logradouro; }\r\n                set { _logradouro = value; }\r\n            }\r\n \r\n            public int Numero\r\n            {\r\n                get { return _numero; }\r\n                set { _numero = value; }\r\n            }\r\n        }\r\n<\/pre>\n<p>Imaginemos agora que nosso projeto \u00e9 um site, e este site utiliza uma class library, contendo as classes Empresa, Endereco e a Interface IObjetoEndereco. Pois bem, com essa mudan\u00e7a na classe Endere\u00e7o, utilizando essa metodologia, n\u00f3s ter\u00edamos que modificar apenas os c\u00f3digos que instanciam a classe Empresa, al\u00e9m claro, de modificar a classe endere\u00e7o, n\u00e3o sendo necess\u00e1rio modificar a classe Empresa dentro da class library. Antes da modifica\u00e7\u00e3o da classe nossas chamadas seriam assim:<\/p>\n<pre class=\"brush: php; title: ; notranslate\" title=\"\">\r\n\r\n      Endereco objEnd = new Endereco();\r\n      Empresa = new Empresa(objEnd);\r\n<\/pre>\n<p>Com a mudan\u00e7a solicitada as chamadas ficariam assim:<\/p>\n<pre class=\"brush: php; title: ; notranslate\" title=\"\">\r\n\r\n      EnderecoPlus objEndPlus = new EnderecoPlus();\r\n      Empresa = new Empresa(objEndPlus);\r\n<\/pre>\n<p>Ou seja, n\u00e3o precisar\u00edamos modificar nossa classe base \u201cEmpresa\u201d, pois seu construtor espera um objeto que implemente a Interface IObjetoEndereco, e tanto a classe Endereco quanto a classe EnderecoPlus s\u00e3o implementa\u00e7\u00f5es da Interface IObjetoEndereco, ou seja, o construtor da classe Empresa pode receber qualquer um dos dois.<\/p>\n<p>Essa metodologia n\u00e3o \u00e9 recomendada para sistemas em que as classes s\u00f3 possam definir construtores vazios, ou seja, onde os construtores das classes n\u00e3o possam receber par\u00e2metros.<\/p>\n<h3><b>Getter e Setter<\/b><\/h3>\n<p>Essa metodologia \u00e9 mais comumente usada para implementar Dependency Injection (DI). Nela a depend\u00eancia dos objetos \u00e9 exposta nas propriedades Get e Set das classes. Essa metodologia possui alguns pontos negativos, pois a inje\u00e7\u00e3o de depend\u00eancia nas propriedades Get e Set quebra alguns conceitos e regras do encapsulamento, ou seja, iremos realizar algo que vai contra os preceitos da orienta\u00e7\u00e3o a objetos.<\/p>\n<p>Segue um exemplo de como implementar essa metodologia:<\/p>\n<pre class=\"brush: php; title: ; notranslate\" title=\"\">\r\n\r\n        public class Empresa\r\n        {\r\n            private IObjetoEndereco _endereco;\r\n \r\n            public IObjetoEndereco Endereco\r\n            {\r\n                get { return _endereco; }\r\n                set { _endereco = value; }\r\n            }\r\n        }\r\n<\/pre>\n<p>Vejam que a propriedade Endereco, trabalha com a Interface IObjetoEndereco para realizar o Get e Set.<\/p>\n<p>Como dito anteriormente, utilizando essa metodologia, deixamos a classe base Empresa livre de refer\u00eancias a classes concretas. Em uma suposta manuten\u00e7\u00e3o precisar\u00edamos modificar apenas a classe Empresa e os trechos de c\u00f3digo que instanciam e utilizam as propriedades de Empresa.<\/p>\n<h3><b>Interface Implementation<\/b><\/h3>\n<p>Nesta metodologia n\u00f3s implementamos uma interface que ficar\u00e1 em um reposit\u00f3rio dentro da camada de IOC (Inversion of Control). Essa Interface declara um m\u00e9todo para injetar o objeto na classe principal.<\/p>\n<p>Vamos ent\u00e3o criar uma nova Interface chamada IObjetoEnderecoDI, a qual ir\u00e1 declarar um m\u00e9todo chamado setEndereco:<\/p>\n<pre class=\"brush: php; title: ; notranslate\" title=\"\">\r\n        public interface IObjetoEnderecoDI\r\n        {\r\n            void setEndereco(IObjetoEndereco obj);\r\n        }\r\n<\/pre>\n<p>Essa Interface ser\u00e1 implementada na classe Empresa. Os c\u00f3digos clientes que ir\u00e3o instanciar um objeto Empresa poder\u00e3o utilizar o m\u00e9todo setEndereco para injetar o objeto Endereco no objeto Empresa.<\/p>\n<p>Agora vamos modificar nossa classe Empresa para codificar o que foi dito acima.<\/p>\n<pre class=\"brush: php; title: ; notranslate\" title=\"\">\r\n\r\n        public class Empresa :IObjetoEnderecoDI\r\n        {\r\n            private IObjetoEndereco _endereco;\r\n \r\n            #region IObjetoEnderecoDI Members\r\n \r\n            public void setEndereco(IObjetoEndereco obj)\r\n            {\r\n                _endereco = obj;\r\n            }\r\n \r\n            #endregion\r\n        }\r\n<\/pre>\n<p>Vejam que a classe Empresa agora herda da nossa nova Interface IObjetoEnderecoDI. Agora ela precisa implementar o m\u00e9todo setEndereco, e neste m\u00e9todo recebemos como par\u00e2metro um objeto do tipo IObjetoEndereco que ser\u00e1 utilizado para setar o campo privado _endereco.<\/p>\n<h3><b>Service Locator<\/b><\/h3>\n<p>Nesta metodologia a classe que ir\u00e1 agregar um objeto filho utiliza uma classe \u201cLocalizadora de Objetos\u201d, para obter a inst\u00e2ncia correta do objeto filho. Essa classe Localizadora n\u00e3o cria inst\u00e2ncias do objeto filho, ela prov\u00ea uma metodologia para registrar e achar os servi\u00e7os que ajudam na cria\u00e7\u00e3o do objeto.<\/p>\n<p>Vamos ao exemplo. Primeiramente vamos criar a classe que ser\u00e1 a Localizadora de Objetos.<\/p>\n<pre class=\"brush: php; title: ; notranslate\" title=\"\">\r\n\r\n       static class LocalizadorEndereco\r\n        {\r\n            public static IObjetoEndereco getEndereco()\r\n            {\r\n                throw new NotImplementedException();\r\n            }\r\n        }\r\n<\/pre>\n<p>Agora vamos utiliza &#8211; l\u00e1 na classe Empresa<\/p>\n<pre class=\"brush: php; title: ; notranslate\" title=\"\">\r\n\r\n       public class Empresa\r\n        {\r\n            private IObjetoEndereco _endereco;\r\n \r\n            public Empresa()\r\n            {\r\n                this._endereco = LocalizadorEndereco.getEndereco();\r\n            }\r\n        }\r\n<\/pre>\n<\/div>\n<p>Veja o leitor que agora nossa classe empresa possui um construtor que chama o Service Locator, para obter a inst\u00e2ncia do objeto Endereco.<\/p>\n<p>A maior vantagem desta metodologia \u00e9 a possibilidade de modificarmos o nosso Service Locator a qualquer momento para definirmos os nossos objetos sempre que precisarmos.<\/p>\n<h4><b>Conclus\u00e3o<\/b><\/h4>\n<p>Amigo leitor vimos neste artigo uma breve explica\u00e7\u00e3o sobre Design Patterns. Vimos tamb\u00e9m um pouco de teoria sobre o Pattern Dependency Injection e como implementar esse Pattern em projetos utilizando a linguagem C#.<\/p>\n<p>Espero que este artigo corrobore com a concep\u00e7\u00e3o de que \u00e9 important\u00edssima a utiliza\u00e7\u00e3o dos Patterns em desenvolvimento de sistemas de software. Ainda hoje, encontramos alguma resist\u00eancia por parte de alguns desenvolvedores, em adotar os conceitos da orienta\u00e7\u00e3o a objetos. Sendo que os Patterns nos oferece diversas perspectivas de implementar orienta\u00e7\u00e3o a objetos, sem d\u00favida alguma s\u00f3 teremos benef\u00edcios na ado\u00e7\u00e3o dos Patterns.<\/p>\n<p>\u00c9 sempre bom lembrar, que \u00e0 primeira vista, desenhar e codificar projetos orientados a objetos e utilizando Design Patterns, pode parecer bastante trabalhoso pela quantidade de c\u00f3digo que \u00e9 escrito. Por\u00e9m precisamos pensar sempre em longo prazo, e neste sentido, com certeza teremos menos trabalho no futuro, pois se precisarmos implementar coisas novas no projeto teremos mais facilidade do que se n\u00e3o utilizarmos Design Patterns.<\/p>\n<p>Terminamos por aqui. Espero que o artigo seja \u00fatil.<\/p>\n<p>Fonte: <a href=\"http:\/\/www.devmedia.com.br\/design-patterns-injecao-de-dependencia-com-c\/23671\" target=\"_blank\">http:\/\/www.devmedia.com.br\/design-patterns-injecao-de-dependencia-com-c\/23671<\/a><\/p>\n","protected":false},"excerpt":{"rendered":"<p>Hoje falaremos sobre algo bastante interessante e \u00fatil na \u00e1rea de Desenvolvimento de Sistemas. Vamos falar sobre Design Patterns. Design Patterns ou Padr\u00f5es de Projetos, de um modo geral, consiste numa s\u00e9rie de modelos de resolu\u00e7\u00e3o de problemas recorrentes em projetos de desenvolvimento de softwares.<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"_exactmetrics_skip_tracking":false,"_exactmetrics_sitenote_active":false,"_exactmetrics_sitenote_note":"","_exactmetrics_sitenote_category":0,"_jetpack_memberships_contains_paid_content":false,"footnotes":""},"categories":[95],"tags":[96,97],"class_list":["post-505","post","type-post","status-publish","format-standard","hentry","category-design-patterns","tag-design-patterns","tag-injecao-de-dependencia"],"jetpack_featured_media_url":"","jetpack_sharing_enabled":true,"_links":{"self":[{"href":"http:\/\/gianfratti.com\/index.php\/wp-json\/wp\/v2\/posts\/505","targetHints":{"allow":["GET"]}}],"collection":[{"href":"http:\/\/gianfratti.com\/index.php\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"http:\/\/gianfratti.com\/index.php\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"http:\/\/gianfratti.com\/index.php\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"http:\/\/gianfratti.com\/index.php\/wp-json\/wp\/v2\/comments?post=505"}],"version-history":[{"count":5,"href":"http:\/\/gianfratti.com\/index.php\/wp-json\/wp\/v2\/posts\/505\/revisions"}],"predecessor-version":[{"id":532,"href":"http:\/\/gianfratti.com\/index.php\/wp-json\/wp\/v2\/posts\/505\/revisions\/532"}],"wp:attachment":[{"href":"http:\/\/gianfratti.com\/index.php\/wp-json\/wp\/v2\/media?parent=505"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"http:\/\/gianfratti.com\/index.php\/wp-json\/wp\/v2\/categories?post=505"},{"taxonomy":"post_tag","embeddable":true,"href":"http:\/\/gianfratti.com\/index.php\/wp-json\/wp\/v2\/tags?post=505"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}