¿Cómo se organizan grandes bases de datos JS/jQuery en todo su sitio web? Hay muchos buenos recursos sobre cómo organizar partes de tu código, pero nada acerca de cómo juntarlo todo y ajustar cada pieza en su lugar: organización de código lateral, varias páginas usando el mismo código, permaneciendo SECO con acoplamiento flojo, etc.¿Cómo se organizan grandes bases de código JS/jQuery en todo su sitio web?
A continuación es cómo me ocupo de ello. Nunca me he sentido cómodo organizando mi código de esta manera, porque creo que es descuidado y puede llevar a problemas de mantenimiento/escalado, pero realmente no sé nada mejor.
Me doy cuenta de que todos tenemos sus propios requisitos y no hay soluciones llave en mano, pero me gustaría escuchar algunas opiniones sobre lo que estoy haciendo mal, POR QUÉ lo estoy haciendo mal y sugerencias sobre cómo escribir un código más fácil de mantener.
Lo que yo creo que realmente estoy tratando de conseguir en:
¿Cómo lidiar con la lógica que necesidad de utilizar en varios lugares, en varias páginas?
¿Cómo se organiza el código de página específico ? ¿Es una buena idea el espacio de nombres de cada página en un objeto global? 1.
¿Qué haces desde el principio para asegurar no estás constantemente re-escribir sus patrones de organización como su aplicación se hace más grande y más grande ? Probablemente estoy en mi 4ta iteración escribiendo esto.2.
Cada página recibe el archivo principal application.js. Cada página adicional tiene su propio archivo application.pagename.js . Utilizo la lógica del lado del servidor para incluir los archivos (primero verificando para ver si alguno existe para la página - algunas páginas no necesitan JS), y luego iniciarlos en orden.
Así que mi página de inicio se ve como:
<script src="js/application.js"></script>
<script src="js/application.index.js"></script>
<script>
MyApp.init();
MyApp.index.init();
</script>
mi convención URL es/página/subpágina/id /. Tengo alrededor de 10 páginas y una gran cantidad de subpáginas, cada subpágina requiere su propia lógica. ver el último ejemplo en esta publicación.
La mayor parte de mi código ya está modularizado en widgets jQuery UI o complementos jQuery, así que diría que el 75% del código en estos archivos requiere() 'un widget y lo inserta.
Uso requireJS para instalar widgets según sea necesario.
// application.js
var MyApp = {
init: function(){
var self = this;
// these widgets are available on every single page
// notice the call to jquery.deparam.js - i'll use this later to init subpage logic.
require(['js/widget1.js', 'js/widget2.js', 'js/widget3.js', 'js/jquery.deparam.js'], function(){
// deparam the query string. I'll use this later.
self.querystring = $.deparam.querystring();
// init widgets once the document is ready
$(function(){
$("#widget1").widget1();
$("#widget2").widget2();
// make these bindings available immediately as well.
self.rebindable();
});
});
},
// I use jQuery UI Dialog extensively as a window manager, and each dialog is loaded
// via an AJAX request. I'll call this method after each AJAX request to
// rebind some key widgets.
rebindable: function(){
$("#widget3").widget3();
}
};
// application.index.js
// home page specific stuff. this file is only included on the home page.
MyApp.index = {
// my convention is that init is automatically called after the script
// is included in a page, outside of a doc.ready statement.
init: function(){
var self = this;
require(['js/widget4.js'], function(){
$(function(){
self.widget4($("#foo"));
});
});
},
// passing elements to each method allows me to call this init code
// outside of the index page. I can require() this file, and only init
// widget4, and even use a different element.
widget4: function(element){
var config = {
something: "custom to the home page"
};
element.widget4(config);
}
};
// application.foo.js
// page "foo" stuff
MyApp.foo = {
init: function(){
var self = this;
// this page happens to use the same widget3 and configuration present
// in MyApp.index. this is where things can get sloppy and unmaintainable
// really quickly.
require(['js/application.index.js'], function(){
$(function(){
MyApp.index.widget3($("#bar"));
});
});
// page "foo" has three subpages (or actions) and require
// their own logic. url convention: /foo/subpage1/
// init whichever page we're on...
switch(self.querystring.subpage){
case "subpage1":
self.subpage1.init();
break;
case "subpage2":
self.subpage2.init();
break;
case "subpage3":
self.subpage3.init();
break;
}
},
subpage1: function(){
init: function(){
var self = this;
// once the DOM is ready init dialog.
$(function(){
self.dialog($("#openDialog"));
});
},
dialog: function(element){
element.bind("click", function(){
$('<div></div>').dialog({
open: function(){
// see what i'm doing here?
MyApp.rebindable();
// maybe more bindings specific to this
// dialog here
}
});
});
}
},
subpage2: function(){
init: function(){
}
},
subpage3: function(){
init: function(){
}
}
};
Estaba pensando en esto yo esta semana. Recientemente me uní a un equipo de proyecto como el principal codificador de JavaScript. El proyecto lleva funcionando más de un año, por lo que tienen javascript por todas partes. Han acumulado una extensa biblioteca de JavaScript y han hecho algunos esfuerzos para usar espacios de nombres, pero muchas páginas tienen JavaScript personalizado que no solo está escrito en páginas y controles de usuario, sino que también se genera en base a datos de control de página o de usuario. Tengo la abrumadora tarea de darle sentido a todo e intentar estandarizar lo más posible. – Silkster
(continuación) Su método es un buen comienzo, pero puedo ver dónde no se puede mantener. Tal vez pueda diseñar un método para configurar páginas y controles para que no tenga que usar muchas instrucciones de conmutación. También puede consultar Claypool (http: // http: //www.claypooljs.com/) para ver si eso podría ayudar. – Silkster
@Silkster el enlace está roto: http: //http//www.claypooljs.com/ –