Projeto Katana e o desenvolvimento web com .NET - Prática

Na parte anterior do post abordamos uma introdução ao projeto Katana e suas motivações, bem como o OWIN (Open Web Interface for .NET). Neste post introduziremos alguns conceitos na prática bem como as bibliotecas necessárias para a construção de aplicações compatíveis com o OWIN através do projeto Katana. Observação: Link para download do código disponível ao final do post.


Criando o projeto

Para reproduzir os mesmos exemplos é necessário o Visual Studio 2013 ou a versão Express 2013 para Web, que pode ser obtida gratuitamente.

Nesta prática criaremos uma pequena aplicação e hospedaremos através do IIS e em seguida reutilizaremos o mesmo projeto em um host customizado através de uma aplicação console.

Para dar inicio criaremos pelo o Visual Studio uma aplicação ASP.NET vazia conforme Figura 1

 

Figura 1 - Criação do projeto

Em seguida crie um novo item na solução. Escolha a opção OWIN Startup Class conforme figura Figura 2. Serão instalados dois pacotes ao projeto ao incluir esta classe, sendo eles o pacote Microsoft.Owin contendo a base para os outros componentes do projeto Katana e o pacote Owin.

Figura 2 - Classe startup e referências adicionadas automaticamente.

A classe criada possui uma convenção, incluindo um método void nomeado Configuration e recebe uma instancia de um objeto que implemente a interface IAppBuilder, permitindo a compatibilidade de servers e hosts não somente utilizando o projeto Katana, mas futuras implementações de servers e hosts de terceiros.

O código da classe startup pode ser conferido a seguir:

using Owin;

[assembly: OwinStartup(typeof(KatanaDemo.Startup))]

namespace KatanaDemo
{
    using AppFunc = Func<IDictionary<string, object>, Task>;

public class Startup
    {
        public void Configuration(IAppBuilder app)
        {
            // app.UseFoo
            // app.UseBar
        }
    }
}


O método Configuration será responsável por registrar todos os componentes middleware para serem executados a cada requisição.

Middleware

Os middlewares são componentes capazes de manusear o objeto Environment Dictionary, definido pela especificação OWIN. O middleware pode ser desde um simples componente de autenticação até um framework completo como o ASP.NET WebApi ou SignalR. A porta de entrada para a comunicação entre o server e o middleware é a assinatura do Application Delegate demonstrado no post anterior.


Servers e Hosts

Dentro do contexto do OWIN, os Hosts podem ser desde um server IIS, até aplicações Windows Forms e Serviços do Windows, sendo ele responsável pelo carregamento e finalização de componentes internos OWIN. Os Servers são responsáveis pela ligação TCP, construir o Environment Dictionary e processar cada um dos componentes registrados no IAppBuilder através da pipeline criada para a execução.

Conforme conferimos na Figura 3, temos o diagrama demonstrando os participantes deste processo e como se associam.

Figura 3 - Fluxo (Host/Server/Pipeline)

Para darmos continuidade, utilizaremos o server demonstrado na Figura 3 denominado SystemWeb, ele permitirá executarmos nossa aplicação dentro da pipeline do ASP.NET onde a mesma atuara como um Host e Server ao mesmo tempo. Para isso instalamos mais um componente do projeto Katana através de PMC. Execute o comando abaixo:

> Install-Package Microsoft.Owin.Host.SystemWeb


Após concluir a instalação criaremos dois middlewares de exemplo em nosso projeto, um será responsável por devolver uma mensagem “hello katana” e o outro responderá qual o path solicitado através da URL digitada.

public class HelloMiddleware
{
    readonly AppFunc _next;

public HelloMiddleware(AppFunc next) { _next = next; }

public async Task Invoke(IDictionary<string, object> env)
    {
        var responseBody = env["owin.ResponseBody"] as Stream;
        var hello = System.Text.Encoding.UTF8.GetBytes("Hello Katana!");
        await responseBody.WriteAsync(hello, 0, hello.Length);

await _next.Invoke(env);
    }
}

public class PathMiddleware : OwinMiddleware
{
    public PathMiddleware(OwinMiddleware next) : base(next) { }

public override async Task Invoke(IOwinContext context)
    {
        await context.Response.WriteAsync(String.Format(" at {0}", context.Request.Path.Value));
        //await Next.Invoke(new OwinContext(env));
    }
}

 

Entenderemos adiante cada middleware, e por hora para utilizar ambos, registraremos na seguinte ordem de nosso método Configuration na classe Startup.


       public void Configuration(IAppBuilder app)

       {

           app.Use<HelloMiddleware>();

           app.Use<PathMiddleware>();

       }


Ao executarmos, nossa aplicação com o velho F5, ao acessarmos uma URL especifica como http://localhost:xxx/path/to/pipeline em nosso navegador, teremos o resultado conforme Figura 4.

Figura 4 - Katana através da pipeline do ASP.NET

Nosso primeiro middleware segue uma convenção padrão respeitando a assinatura do Application Delegate, ou seja nosso método Invoke é assíncrono, e recebe o objeto Environment Dictionary, no exemplo obtivemos o objeto que corresponde ao corpo de resposta HTTP com a chave conforme a especificação OWIN descreve e escrevemos uma mensagem no objeto Stream. O segundo middleware é mais interessante pois herdamos de uma classe de auxilio do projeto Katana que visa facilitar a criação de middlewares, facilitando a manipulação de dados do Environment Dictionary de maneira tipada provendo um objeto do tipo OwinContext. Veja que internamente existem alguns recursos para facilitar a execução dos middlewares seguintes de forma encadeada, recebermos o próximo middleware a ser executado e decidirmos se o mesmo poderá ser executado ou não, este tipo de recurso é útil em cenários de autenticação.


Usando uma Framework real

Desta vez utilizaremos um framework real em nossa aplicação, o ASP.NET WebApi. Comecemos instalando o pacote que habilita o WebApi para o uso com o OWIN. Pelo PMC execute o seguinte comando:

> Install-Package Microsoft.AspNet.WebApi.Owin

 

Após instalação, criamos um controller conforme abaixo em nosso projeto:

public class ValuesController : ApiController
    {
        public string[] Get()
        {
            return new[] { "SignalR", "ASP.NET MVC", "WebApi", "WebPages", "WebForms" };
        }
    }

 

E registramos o WebApi em nosso objeto IAppBuilder através de um extension method chamada UseWebApi conforme abaixo, incluída com o pacote que acabamos de instalar.

//..outras diretivas using

using System.Web.Http;

public void Configuration(IAppBuilder app)
{
    var httpConfig = new HttpConfiguration();
    httpConfig.Routes.MapHttpRoute("default", "api/{controller}");

app.UseWebApi(httpConfig);

//… outros middlewares
}

 

Ao executarmos nossa aplicação e entrarmos com a URL http://localhost:xxx/api/values teremos o seguinte resultado conforme Figura 5.

 

 

Figura 5 - WebApi em ação

Com isso podemos utilizar o conhecimento que já temos para criar nossas aplicações utilizando outros frameworks disponíveis e compatíveis com o OWIN como ASP.NET SignalR ou NancyFx.


Portando a aplicação

Antes de concluirmos os exemplos vamos portar esta aplicação para execução em outro ambiente. Para tal, crie uma novo projeto neste mesmo solution utilizado, do tipo Console Application e inclua uma referência de nosso projeto anterior. Observação: Caso esteja no Visual Studio Express, crie o projeto como uma Class Library (Biblioteca de Classes *.dll) e através das propriedades (Alt+Enter) troque o output para Console Application conforme Figura 6.

 

 

Figura 6

Para prosseguir, inclua os mesmos pacotes que foram incluídos no projeto anterior desta mesma solution, com exceção do server SystemWeb, que desta vez será substituído por dois outros componentes do projeto Katana. O primeiro, Microsoft.Owin.Hosting responsável por prover as classes necessárias para realizarmos o Host em um processo customizado, e segundo, o server Microsoft.Owin.Host.HttpListener. Observação: Necessário trocar o projeto Default no PMC para que sejam incluindo os novos pacotes no projeto correto. Execute o comando abaixo.

> Install-Package Microsoft.Owin.Hosting

> Install-Package Microsoft.Owin.Host.HttpListener


Em nossa classe Program do novo projeto incluímos o código abaixo. Inclua as referencias através da diretiva using para enxergar a classe Startup criada no projeto web anteriormente.

public static void Main(string[] args)
{
    var app = WebApp.Start<Startup>("http://localhost:1234");

Console.WriteLine("Pressione Enter para fechar...");
    Console.ReadKey();

app.Dispose();
}

 

Ao rodar a aplicação com o F5, teremos o mesmo resultado do outro projeto porem fora do ambiente do IIS conforme Figura 7.

 

 

Figura 7 - Self-Hosting em ação

Conclusão

Conforme conferimos, foi introduzido os conceitos práticos iniciais para a utilização do projeto Katana e o porte de uma aplicação OWIN para outro Host e Server sem necessidade de alteração no código fonte. Seria possível portar para outras plataformas como o runtime Mono ao invés do .NET Framework. Esta independência abre caminhos para muitos recursos, incluindo ferramentas para automação de testes de integração sem a necessidade de levantar o IIS, e isto é só a ponta do que é possível fazer. Vamos ficar atentos aos próximos passos do projeto Katana através do seu Roadmap e as contribuições ao OWIN criados pela comunidade. Para maiores detalhes consulte as referências deste post. Até a próxima e bons estudos!!!

Código utilizado neste post:

http://sdrv.ms/1amhhoQ.


Referências:

http://owin.org

http://katanaproject.codeplex.com

http://www.asp.net/aspnet/overview/owin-and-katana/an-overview-of-project-katana

http://msdn.microsoft.com/en-us/magazine/dn451439.aspx

Exibições: 581

Comentar

Você precisa ser um membro de DevBrasil para adicionar comentários!

Entrar em DevBrasil

© 2017   Criado por Ramon Durães.   Ativado por

Badges  |  Relatar um incidente  |  Termos de serviço