fix not full rerendering bug and add log to route objects
Project: http://git-wip-us.apache.org/repos/asf/couchdb/repo Commit: http://git-wip-us.apache.org/repos/asf/couchdb/commit/dee460ce Tree: http://git-wip-us.apache.org/repos/asf/couchdb/tree/dee460ce Diff: http://git-wip-us.apache.org/repos/asf/couchdb/diff/dee460ce Branch: refs/heads/route-events Commit: dee460ce4e8b4c53717c5ff29162d47779fe6d39 Parents: 64d7eed Author: Garren Smith <[email protected]> Authored: Wed Apr 24 15:57:15 2013 +0200 Committer: Garren Smith <[email protected]> Committed: Thu May 9 09:59:58 2013 +0200 ---------------------------------------------------------------------- src/fauxton/app/addons/logs/routes.js | 57 +++-- src/fauxton/app/api.js | 28 ++- src/fauxton/app/modules/databases/routes.js | 10 +- src/fauxton/app/modules/documents/routes.js | 324 +++++++++++++--------- src/fauxton/app/router.js | 14 +- 5 files changed, 264 insertions(+), 169 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/couchdb/blob/dee460ce/src/fauxton/app/addons/logs/routes.js ---------------------------------------------------------------------- diff --git a/src/fauxton/app/addons/logs/routes.js b/src/fauxton/app/addons/logs/routes.js index 4e04d08..177032c 100644 --- a/src/fauxton/app/addons/logs/routes.js +++ b/src/fauxton/app/addons/logs/routes.js @@ -11,37 +11,48 @@ // the License. define([ - "app", + "app", - "api", + "api", - // Modules - "addons/logs/resources" + // Modules + "addons/logs/resources" ], function(app, FauxtonAPI, Log) { - Log.Routes = { - "_log": function() { - var logs = new Log.Collection(); - - return { - layout: "with_sidebar", - crumbs: [ - {"name": "Logs", "link": "_log"} - ], - views: { - "#dashboard-content": new Log.Views.View({collection: logs}), - "#sidebar-content": new Log.Views.FilterView({}) - }, - apiUrl: logs.url(), - establish: function() { - return [logs.fetch()]; - } - }; + var LogRouteObject = FauxtonAPI.RouteObject.extend({ + layout: "with_sidebar", + + crumbs: [ + {"name": "Logs", "link": "_log"} + ], + + routes: ["_log"], + + apiUrl: function() { + return this.logs.url(); + }, + + views: function () { + this.logs = new Log.Collection(); + this.setView("#dashboard-content", new Log.Views.View({collection: this.logs})); + this.setView("#sidebar-content", new Log.Views.FilterView({})); + return {}; + }, + + route: function() { + console.log('boom'); + }, + + establish: function() { + return [this.logs.fetch()]; } - }; + }); + + Log.RouteObjects = [new LogRouteObject()]; return Log; }); + http://git-wip-us.apache.org/repos/asf/couchdb/blob/dee460ce/src/fauxton/app/api.js ---------------------------------------------------------------------- diff --git a/src/fauxton/app/api.js b/src/fauxton/app/api.js index 2c68086..c6c3c69 100644 --- a/src/fauxton/app/api.js +++ b/src/fauxton/app/api.js @@ -111,7 +111,7 @@ function(app, Fauxton) { _.extend(FauxtonAPI.RouteObject.prototype, Backbone.Events, { // Should these be default vals or empty funcs? - views: {}, + _views: {}, routes: {}, events: {}, data: {}, @@ -139,6 +139,7 @@ function(app, Fauxton) { if (this.renderedState === true) { this.rerender.apply(this, arguments); } else { + this.preloadViews(); this.renderWith.apply(this, arguments); } }, @@ -149,15 +150,16 @@ function(app, Fauxton) { masterLayout.setTemplate(this.layout); masterLayout.clearBreadcrumbs(); + var crumbs = this.get('crumbs'); - if (this.crumbs.length) { + if (crumbs.length) { masterLayout.setBreadcrumbs(new Fauxton.Breadcrumbs({ - crumbs: this.crumbs + crumbs: crumbs })); } $.when.apply(this, this.establish()).done(function(resp) { - _.each(routeObject.views, function(view, selector) { + _.each(routeObject.getViews(), function(view, selector) { masterLayout.setView(selector, view); $.when.apply(null, view.establish()).then(function(resp) { @@ -183,11 +185,17 @@ function(app, Fauxton) { }); if (this.get('apiUrl')) masterLayout.apiBar.update(this.get('apiUrl')); - + // Track that we've done a full initial render this.renderedState = true; }, + preloadViews: function () { + _.each(this.get('views'), function (view, selector) { + this.setView(selector, view); + }, this); + }, + get: function(key) { return _.isFunction(this[key]) ? this[key]() : this[key]; }, @@ -211,16 +219,20 @@ function(app, Fauxton) { }, getView: function(selector) { - return this.views[selector]; + return this._views[selector]; }, setView: function(selector, view) { - this.views[selector] = view; + this._views[selector] = view; return view; }, getViews: function() { - return this.views; + return this._views; + }, + + clearViews: function () { + this._views = {}; } }); http://git-wip-us.apache.org/repos/asf/couchdb/blob/dee460ce/src/fauxton/app/modules/databases/routes.js ---------------------------------------------------------------------- diff --git a/src/fauxton/app/modules/databases/routes.js b/src/fauxton/app/modules/databases/routes.js index b7f1dbb..ee3f84e 100644 --- a/src/fauxton/app/modules/databases/routes.js +++ b/src/fauxton/app/modules/databases/routes.js @@ -35,24 +35,30 @@ function(app, FauxtonAPI, Databases, Views) { return this.databases.url(); }, - initialize: function() { + views: function() { this.databases = new Databases.List(); this.deferred = FauxtonAPI.Deferred(); this.databasesView = this.setView("#dashboard-content", new Views.List({ collection: this.databases })); + + this.databasesView.setPage(this.dbPage); + this.sidebarView = this.setView("#sidebar-content", new Views.Sidebar({ collection: this.databases })); + + return {}; }, route: function() { var params = app.getParams(); - this.databasesView.setPage(params.page); + this.dbPage = params.page; }, rerender: function() { + this.databasesView.setPage(this.dbPage); this.databasesView.render(); }, http://git-wip-us.apache.org/repos/asf/couchdb/blob/dee460ce/src/fauxton/app/modules/documents/routes.js ---------------------------------------------------------------------- diff --git a/src/fauxton/app/modules/documents/routes.js b/src/fauxton/app/modules/documents/routes.js index ffed186..488865b 100644 --- a/src/fauxton/app/modules/documents/routes.js +++ b/src/fauxton/app/modules/documents/routes.js @@ -11,13 +11,13 @@ // the License. define([ - "app", + "app", - "api", + "api", - // Modules - "modules/documents/resources", - "modules/databases/base" + // Modules + "modules/documents/resources", + "modules/databases/base" ], function(app, FauxtonAPI, Documents, Databases) { @@ -96,8 +96,8 @@ function(app, FauxtonAPI, Documents, Databases) { data.designDocs = new Documents.AllDocs(null, { database: data.database, params: {startkey: '"_design"', - endkey: '"_design1"', - include_docs: true} + endkey: '"_design1"', + include_docs: true} }); return { @@ -178,20 +178,33 @@ function(app, FauxtonAPI, Documents, Databases) { }; }; - Documents.Routes = { - //"database/:database/:doc/code_editor": codeEditorCallback, - //"database/:database/:doc": codeEditorCallback, - "database/:database/_design%2F:doc": function(database, doc) { - var docID = "_design/"+doc; - return codeEditorCallback(database, docID); + + var DocumentsRouteObject = FauxtonAPI.RouteObject.extend({ + layout: "with_tabs_sidebar", + + crumbs: function () { + return [ + {"name": "Databases", "link": "/_all_dbs"}, + {"name": this.data.database.id, "link": Databases.databaseUrl(this.data.database)} + ]; + }, + + routes: ["database/:database/_all_docs(:extra)"], + + apiUrl: function() { + return this.data.database.allDocs.url(); + }, + + route: function(route, params) { + this.databaseName = params[0]; }, - "database/:database/_all_docs(:extra)": function(databaseName, page) { - var data = { - database: new Databases.Model({id:databaseName}) + views: function () { + this.data = { + database: new Databases.Model({id:this.databaseName}) }; - data.designDocs = new Documents.AllDocs(null, { - database: data.database, + this.data.designDocs = new Documents.AllDocs(null, { + database: this.data.database, params: {startkey: '"_design"', endkey: '"_design1"', include_docs: true} @@ -199,144 +212,187 @@ function(app, FauxtonAPI, Documents, Databases) { var options = app.getParams(); options.include_docs = true; - data.database.buildAllDocs(options); + this.data.database.buildAllDocs(options); - return { - layout: "with_tabs_sidebar", + this.setView("#dashboard-content", new Documents.Views.AllDocsList({ + collection: this.data.database.allDocs + })); - data: data, + this.setView("#sidebar-content", new Documents.Views.Sidebar({ + collection: this.data.designDocs + })); - crumbs: [ - {"name": "Databases", "link": "/_all_dbs"}, - {"name": data.database.id, "link": Databases.databaseUrl(data.database)} - ], + this.setView("#tabs", new Documents.Views.Tabs({ + collection: this.data.designDocs, + database: this.data.database + })); - views: { - "#dashboard-content": new Documents.Views.AllDocsList({ - collection: data.database.allDocs - }), + return {}; + } + }); - "#sidebar-content": new Documents.Views.Sidebar({ - collection: data.designDocs - }), - "#tabs": new Documents.Views.Tabs({ - collection: data.designDocs, - database: data.database - }) - }, - apiUrl: data.database.allDocs.url() - }; - }, - "database/:database/_changes(:params)": function(databaseName, params) { - var data = { - database: new Databases.Model({id:databaseName}) - }; + /* Documents.Routes = { + //"database/:database/:doc/code_editor": codeEditorCallback, + //"database/:database/:doc": codeEditorCallback, + "database/:database/_design%2F:doc": function(database, doc) { + var docID = "_design/"+doc; + return codeEditorCallback(database, docID); + }, - var options = app.getParams(); - data.database.buildChanges(options); + "database/:database/_all_docs(:extra)": function(databaseName, page) { + var data = { +database: new Databases.Model({id:databaseName}) +}; +data.designDocs = new Documents.AllDocs(null, { +database: data.database, +params: {startkey: '"_design"', +endkey: '"_design1"', +include_docs: true} +}); - return { - layout: "with_tabs", +var options = app.getParams(); +options.include_docs = true; +data.database.buildAllDocs(options); - data: data, +return { +layout: "with_tabs_sidebar", - crumbs: [ - {"name": "Databases", "link": "/_all_dbs"}, - {"name": data.database.id, "link": Databases.databaseUrl(data.database)}, - {"name": "_changes", "link": "/_changes"} - ], +data: data, - views: { - "#dashboard-content": new Documents.Views.Changes({ - model: data.database - }), +crumbs: [ +{"name": "Databases", "link": "/_all_dbs"}, +{"name": data.database.id, "link": Databases.databaseUrl(data.database)} +], - "#tabs": new Documents.Views.Tabs({ - collection: data.designDocs, - database: data.database, - active_id: 'changes' - }) - }, +views: { +"#dashboard-content": new Documents.Views.AllDocsList({ +collection: data.database.allDocs +}), - apiUrl: data.database.changes.url() - }; - }, +"#sidebar-content": new Documents.Views.Sidebar({ +collection: data.designDocs +}), - "database/:database/new": newDocCodeEditorCallback, - "database/:database/new_view": newViewEditorCallback, - - // TODO: fix optional search params - // Can't get ":view(?*search)" to work - // However ":view?*search" does work - //"database/:database/_design/:ddoc/_view/:view(\?*options)": function(databaseName, ddoc, view, options) { - "database/:database/_design/:ddoc/_view/:view": function(databaseName, ddoc, view, options) { - // hack around backbone router limitations - view = view.replace(/\?.*$/,''); - var params = app.getParams(); - var data = { - database: new Databases.Model({id:databaseName}) - }; +"#tabs": new Documents.Views.Tabs({ +collection: data.designDocs, +database: data.database +}) +}, - data.indexedDocs = new Documents.IndexCollection(null, { - database: data.database, - design: ddoc, - view: view, - params: params - }); +apiUrl: data.database.allDocs.url() +}; +}, - data.designDocs = new Documents.AllDocs(null, { - database: data.database, - params: {startkey: '"_design"', - endkey: '"_design1"', - include_docs: true} - }); +"database/:database/_changes(:params)": function(databaseName, params) { +var data = { +database: new Databases.Model({id:databaseName}) +}; - var ddocInfo = { - id: "_design/" + ddoc, - currView: view, - designDocs: data.designDocs - }; +var options = app.getParams(); +data.database.buildChanges(options); - return { - layout: "with_tabs_sidebar", - - data: data, - // TODO: change dashboard-content - views: { - "#dashboard-content": new Documents.Views.AllDocsList({ - collection: data.indexedDocs, - nestedView: Documents.Views.Row, - viewList: true, - ddocInfo: ddocInfo, - params: params - }), - - "#sidebar-content": new Documents.Views.Sidebar({ - collection: data.designDocs, - ddocInfo: ddocInfo - }), - - "#tabs": new Documents.Views.Tabs({ - collection: data.designDocs, - database: data.database - }) - }, - - crumbs: [ - {"name": "Databases", "link": "/_all_dbs"}, - {"name": data.database.id, "link": Databases.databaseUrl(data.database)}, - {"name": ddoc + "/" + view, "link": data.indexedDocs.url()} - ], - // TODO: change to view URL - apiUrl: data.indexedDocs.url() - }; - } +return { +layout: "with_tabs", + +data: data, + +crumbs: [ +{"name": "Databases", "link": "/_all_dbs"}, +{"name": data.database.id, "link": Databases.databaseUrl(data.database)}, +{"name": "_changes", "link": "/_changes"} +], + +views: { + "#dashboard-content": new Documents.Views.Changes({ +model: data.database +}), + + "#tabs": new Documents.Views.Tabs({ +collection: data.designDocs, +database: data.database, +active_id: 'changes' +}) +}, + +apiUrl: data.database.changes.url() + }; +}, + + "database/:database/new": newDocCodeEditorCallback, + "database/:database/new_view": newViewEditorCallback, + + // TODO: fix optional search params + // Can't get ":view(?*search)" to work + // However ":view?*search" does work + //"database/:database/_design/:ddoc/_view/:view(\?*options)": function(databaseName, ddoc, view, options) { + "database/:database/_design/:ddoc/_view/:view": function(databaseName, ddoc, view, options) { + // hack around backbone router limitations + view = view.replace(/\?.*$/,''); + var params = app.getParams(); + var data = { +database: new Databases.Model({id:databaseName}) + }; + + data.indexedDocs = new Documents.IndexCollection(null, { +database: data.database, +design: ddoc, +view: view, +params: params +}); + +data.designDocs = new Documents.AllDocs(null, { +database: data.database, +params: {startkey: '"_design"', +endkey: '"_design1"', +include_docs: true} +}); + +var ddocInfo = { +id: "_design/" + ddoc, + currView: view, + designDocs: data.designDocs +}; + +return { +layout: "with_tabs_sidebar", + + data: data, + // TODO: change dashboard-content + views: { + "#dashboard-content": new Documents.Views.AllDocsList({ +collection: data.indexedDocs, +nestedView: Documents.Views.Row, +viewList: true, +ddocInfo: ddocInfo, +params: params +}), + + "#sidebar-content": new Documents.Views.Sidebar({ +collection: data.designDocs, +ddocInfo: ddocInfo +}), + + "#tabs": new Documents.Views.Tabs({ +collection: data.designDocs, +database: data.database +}) +}, + +crumbs: [ +{"name": "Databases", "link": "/_all_dbs"}, +{"name": data.database.id, "link": Databases.databaseUrl(data.database)}, +{"name": ddoc + "/" + view, "link": data.indexedDocs.url()} +], + // TODO: change to view URL + apiUrl: data.indexedDocs.url() }; +} +};*/ - Documents.RouteObjects = [new DocEditorRouteObject()]; +Documents.RouteObjects = [/*new DocEditorRouteObject(),*/ new DocumentsRouteObject()]; return Documents; }); http://git-wip-us.apache.org/repos/asf/couchdb/blob/dee460ce/src/fauxton/app/router.js ---------------------------------------------------------------------- diff --git a/src/fauxton/app/router.js b/src/fauxton/app/router.js index 45fd282..c2270df 100644 --- a/src/fauxton/app/router.js +++ b/src/fauxton/app/router.js @@ -99,20 +99,29 @@ function(req, app, Initialize, FauxtonAPI, Fauxton, Layout, Databases, Documents var Router = app.router = Backbone.Router.extend({ routes: {}, + routeObjects: [], // These moduleRoutes functions are aguably better outside but // need access to the Router instance which is not created in this // module addModuleRoute: function(generator, route) { - this.route(route, route.toString(), generateRoute(generator, route)); + //this.route(route, route.toString(), generateRoute(generator, route)); }, addModuleRouteObject: function(routeObject) { + var self = this; + this.routeObjects.push(routeObject); + console.log(routeObject); var masterLayout = this.masterLayout; _.each(routeObject.get('routes'), function(route) { - //this.route(route, route.toString(), _.partial(routeObject.renderWith, route, this.masterLayout)); this.route(route, route.toString(), function() { + if (self.activeRouteObject && routeObject !== self.activeRouteObject) { + self.activeRouteObject.renderedState = false; + } + routeObject.render(route, masterLayout, Array.prototype.slice.call(arguments)); + + self.activeRouteObject = routeObject; }); }, this); }, @@ -130,6 +139,7 @@ function(req, app, Initialize, FauxtonAPI, Fauxton, Layout, Databases, Documents // This is pure routes the addon provides if (module.Routes) { _.each(module.Routes, this.addModuleRoute, this); + _.each(module.RouteObjects, this.addModuleRouteObject, this); } } }, this);
