2012-03-08 12 views
12

Me gustaría detectar las excepciones lanzadas desde las devoluciones de llamadas pasadas a jQuery (ya sea a controladores de eventos como click, oa métodos jqXHR como then o always).¿Cómo atrapar las excepciones lanzadas en las devoluciones de llamadas pasadas a jQuery?

He identificado dos opciones:

  • window.onerror manipulador - esto es sólo una solución parcial, ya que no es compatible con Android, que es uno de mis plataformas de destino
  • manejo de excepciones dentro de cada individuo de devolución de llamada - ¡NO SECO en absoluto!

La única otra cosa que se me ocurre es anular los métodos de jQuery, pero eso puede ocasionar problemas cada vez que actualizo jQuery. Para los manejadores de AJAX, posiblemente podría usar $ .ajaxSetup (por la respuesta a Exceptions thrown in jQuery AJAX callbacks swallowed?) pero no estoy seguro de que me permita capturar todo.

¿Hay alguna otra opción?

Respuesta

15

se puede envolver cada una devolución de llamada como esto:

function cbWrapper(fn) { 
    return function() { 
     try { 
      return(fn.apply(this, arguments)); 
     } catch(e) { 
      // handle all your exceptions here 
     } 
    }; 
} 

Por lo tanto, cuando se va a pasar una devolución de llamada a una llamada Ajax, en lugar de pasar la devolución de llamada real, se pasa cbWrapper(callback).

$.get(url, cbWrapper(myRealCallback)); 

o la versión anónima en línea sería así:

$.get(url, cbWrapper(function() { 
    // actual callback code here 
})); 

Una forma más avanzada de hacerlo sería para anular $.get() con su propia aplicación que envuelve la devolución de llamada automática, pero que se complica porque jQuery es tan flexible acerca de qué argumentos se pasan realmente. Debido a eso y porque tiene que anular un argumento específico para que esto funcione, debería duplicar todo su código de detección de argumento que determina qué argumentos están presentes y cuáles corresponden a los parámetros de función reales. Ese código es un poco complicado. Es factible y probablemente no se rompa porque si jQuery lo rompió, entonces el código jQuery existente se rompería, pero no está muy limpio.

Si todo es su propio código, que sólo podría hacer su propia versión de $.get() que no es tan flexible con posiciones de argumentos y cambiar todo el código para utilizarlo en lugar del real $.get():

jQuery.fn.myGet = function(url, fn) { 
    return(jQuery.get(url, cbWrapper(fn))); 
} 
Cuestiones relacionadas