2012-05-13 23 views
6

Tengo el problema con HTTPHandlers reutilizables. Quería comprobar cómo funciona la propiedad IsReusable. Así que he creado dos manipuladores:HTTPHandler e IsReusable con WebHandler

reutilizable:

public class ReusableHandler : IHttpHandler 
{ 
    public bool IsReusable 
    { 
     get { return true; } 
    } 

    private int _counter; 

    public ReusableHandler() 
    { 
     _counter = 0; 
    } 

    public void ProcessRequest(HttpContext context) 
    { 
     context.Response.Write("Reusable: " + _counter++); 
    } 

} 

Y no reutilizables:

public class NonReusableHandler : IHttpHandler 
{ 
    public bool IsReusable 
    { 
     get { return false; } 
    } 

    private int _counter; 

    public NonReusableHandler() 
    { 
     _counter = 0; 
    } 

    public void ProcessRequest(HttpContext context) 
    { 
     context.Response.Write("NonReusable: " + _counter++); 
    } 

} 

Ambos trabajan como se esperaba: reutilizable cada tiempo vuelve valor incrementado, mientras que no reutilizable cada devuelve 0 hora. Pero cuando uso mis manejadores como WebHandlers (* .ashx) ambos devuelven 0 cada vez (el código es exactamente el mismo). ¿Significa que cuando uso WebHandlers se ignora la propiedad IsReusable?

Respuesta

2

La configuración predeterminada de .NET es usar el tipo System.Web.UI.SimpleHandlerFactory para manejar las solicitudes de *.ashx. Puede verificar esto mirando la sección Http Handlers en el Administrador de IIS.

Si mira el código fuente de esta fábrica, puede ver que no marca la propiedad IsReusable. También es apátrida, no almacena en caché las instancias creadas. Para ver una clase de fábrica que está usando esta propiedad, mira System.Web.Configuration.HandlerFactoryWrapper.

Ahora, si mira System.Web.HttpApplication.RecycleHandlers(), verá que solo llama indirectamente al método System.Web.IHttpHandlerFactory.ReleaseHandler() (la memoria caché de fábrica mencionada en el párrafo siguiente no maneja el almacenamiento en caché de instancias por sí mismo). La aplicación ignora la propiedad IsReusable (se supone que la fábrica debe hacer eso) y como se descubrió anteriormente, los archivos .ashx usan una fábrica que no reutiliza las instancias.

También vale la pena señalar que System.Web.HttpApplication.GetFactory() parece estar utilizando una memoria caché, pero esa memoria caché solo almacenará la instancia de la fábrica (si está especificada). Si no se especifica una fábrica explícita, el método creará el HandlerFactoryWrapper mencionado anteriormente (que a su vez almacenará en caché las instancias del manejador).

Hasta donde puedo ver, no hay una clase de fábrica en .NET Framework que pueda usar en lugar de SimpleHandlerFactory (la HandlerFactoryWrapper no tiene constructor sin parámetros) aunque puede crear la suya propia.

Cuestiones relacionadas