Thursday, August 21, 2008

MTU (0 de N) : EventHelpers

Introducción

La intención de este post es ser el primero de una serie para documentar algunos métodos extensores que además de considerarlos potencialmente útiles cumplen con las guías de diseño que promueven los expertos en el tema [1].

En lo adelante dividiremos los métodos extensores en dos categorías, aquellos que sirven de puntos de entrada para el uso de LINQ to Objects (lógicamente los más importantes), y otros que responden  al nombre de Helpers. Es decir métodos cuya existencia "nos viene como anillo al dedo" permitiendo evitar el repetir código o patrones de código sin que esto afecta la legibilidad del todo que queramos implementar.

EventHelpers

Hace unas semanas tuve necesidad de implementar una colección que tuviera como añadido la notificación de cambios en la misma mediante eventos. En lugar de escribir por enésima vez el mismo patrón de publicación/subscripción de eventos, decidí probar y crear un método extensor que tomando ventaja del uso de los delegados genéricos (EventHandler<T>) permitiera publicar correctamente el evento escribiendo la menor cantidad de código posible. La noción de publicar eventos correctamente, podemos encontrarla en el capítulo 6 de [2].

En pocas palabras, validar si el delegado asociado al evento no está vacio para posteriormente ejecutar uno a uno los elementos de la lista de invocación, protegiéndonos de que al ejecutarlos ninguna excepción ascienda hasta nuestro código garantizando la correcta finalización del proceso de notificación. Una vez escrito el código seria:

public static void InvokeSafely<T>(this EventHandler<T> del, object sender, T data) where T : EventArgs
{
if (del != null)
del.GetInvocationList().ForEachNoExceptions(d => d.DynamicInvoke(sender, data));
}
public static void ForEachNoExceptions<T>(this T[] array, Action<T> action)
{
Array.ForEach(array, element => { try { action(element); } catch { } });
}

Una vez en ámbito el código se reduce considerablemente, centralizando el proceso para futuras modificaciones.


eventHelpers0


Ahora bien, tomando este pequeño experimento podemos llevar la clase EventHelpers (propuesta en [2]) a la manera de los métodos extensores. La misma podéis descargarla del sitio de O'Reilly.


esperando haberles sido útil, me despido :)


Referencias


[1] Hernández, Octavio. C# 3.0 y LINQ. s.l. : Krasis Press, 2008.


[2] Lowy, Juwal. DotNet Components 2nd Edition. s.l. : O'Reilly Press, 2005.


PD: MTU son las siglas para Metodos Extensores Utiles.