Ver Mensaje Individual
  #2 (permalink)  
Antiguo 03/05/2008, 09:38
Avatar de Negora
Negora
 
Fecha de Ingreso: agosto-2003
Mensajes: 122
Antigüedad: 20 años, 8 meses
Puntos: 5
Re: Importación / Cargador de librerías o módulos

Hola de nuevo:

Si alguien ha probado el código, habrá notado que falla. Se debe a que me olvidé de que "eval" ejecuta el código en el entorno de variables (scope) actual, por lo que todo el contenido de las librerías se carga dentro del objeto y no en window, como debería de ser.

Por todo ello, la solución pasa por ejecutar eval en window, o bien usar el método call (propio de toda función en JavaScript):

Código:
eval.call (window, req.responseText);
Esto funciona bien en Mozilla y Opera pero, para "variar", no en IE. Es absurdo, como siempre.


Para acabar con el problema, he rediseñado la clase, la he hecho instanciable, y la llamo desde window, ya que es la única manera de forzar ese "scope" de variables.

Os presento el nuevo código:

Código:
	// Clase y constructor
	function LibLoader () {
		
		// Matriz de librerías.
		this.arr_lib = ["cssquery", "core", "client", "init", "flash", "check", "form", "vfx", "vfxds"];
		
		// Ruta base de los scripts.
		this.urlbase = "";
		
		// Código absoluto de todas las librerías.
		this.code = "";

		// Matriz de objetos Script.
		this.arr_script = [];
		
		// Llama al método de inicialización.
		this.init ();
		
	}

		// Método de inicialización.
		LibLoader.prototype.init = function () {

			// Obtiene la ruta base de este script, ya que cada documento
			// XHTML se encuentra en diferente lugar y dicha ruta variará.
			var darr_script = document.getElementsByTagName ("script");
			for (var i = 0; i < darr_script.length; i++) {
				if (darr_script [i].src.indexOf ("sys/js/load.js") != -1) {
					this.urlbase = darr_script [i].src.replace ("load.js", "");
					break;
				}
			}
			
			// Crea un objeto para AJAX y otro de tipo Script.
			var req = new XMLHttpRequest ();
			var script = document.createElement ("script");
			script.type = "text/javascript";

			// Recorre la lista de nombres de librería.
			for (var i = 0; i < this.arr_lib.length; i++) {
				
				// Descarga la librería actual de forma síncrona y adjunta su
				// código.
				req.open ("GET", this.urlbase + this.arr_lib [i] + ".js", false);
				req.send (null);
				this.code += req.responseText;
				
				// Crea una copia del objeto Script con la URL de la librería
				// actual.
				script.src = this.urlbase + this.arr_lib [i] + ".js";
				this.arr_script.push (script.cloneNode (true));
				
			}

		};
	
		// Devuelve el código de todas las librerías.
		LibLoader.prototype.getCode = function () {
			return this.code;
		};
		
		// Devuelve la matriz de objetos Script.
		LibLoader.prototype.getScripts = function () {
			return this.arr_script;
		};
	

	// ESTO YA ES CÓDIGO QUE SE EJECUTA EN EL ENTORNO DE WINDOW,
	// NO EN LA CLASE.

	// Instancia la clase LibLoader.
	var $LIBLOADER = new LibLoader ();

	// Carga y evalua todo el código descargado. Se realiza una captura mediante
	// "try" para que en caso de error, la consola no indique que se debe a la
	// sentencia eval. Así, si se produce un error, lo que se hace es adjuntar
	// los objetos Script a la cabecera para que el navegador pueda detectar
	// el error y mostrar su traza en la consola, incluyendo número de línea,
	// lo cual es muy útil.
	try {
		eval ($LIBLOADER.getCode ());
	} catch (_ex) {
		for (var i = 0; i < $LIBLOADER.getScripts ().length; i++) {
			document.getElementsByTagName ("head") [0].appendChild ($LIBLOADER.getScripts () [i]);
		}
	}