Search code examples
javascriptbackbone.jsbackbone-routing

Backbone client router: how to optimize


I have the following route configuration:

routes: {
    '': 'landing_page', 
    ':show_page': 'show_page', 
    '*actions': 'defaultAction' 
    }, 

"Show page" contains a function that goes somewhat like this:

show_page: function(page_name){
        $.get('php/User/check_session.php', _.bind(function(status) {
            if(status == "yes"){
                switch(page_name){

                    case "home": 
                        var home_View = new Home_View(); 
                        app.views.resultView.showView(home_View); 
                        break; 

                    case "parents": 
                        var parent_View = new Parent_View(); 
                        app.views.resultView.showView(parent_View); 
                        break; 

                    case "insurers": 
                        var insurer_View = new Insurer_View(); 
                        app.views.resultView.showView(insurer_View); 
                        break; 

                    case "new_role": 
                        var new_roles_View = new New_roles_View(); 
                        app.views.resultView.showView(new_roles_View); 
                        break; 

                    case "roles_permissions": 
                        var roles_permissions_View = new Roles_permissions_View(); 
                        app.views.resultView.showView(roles_permissions_View); 
                        break; 

                    case "user_roles": 
                        var user_roles_View = new User_roles_View(); 
                        app.views.resultView.showView(user_roles_View); 
                        break; 

                    case "new_accounting": 
                        var input_accounting_View = new Input_accounting_View(); 
                        app.views.resultView.showView(input_accounting_View); 
                        break; 

                    default:
                        var home_View = new Home_View(); 
                        app.views.resultView.showView(home_View); 
                        this.navigate("/home", {trigger:true}); 
                        break; 
                };
etc... 

Now the problem is that I want to get the route of something like:

':show_page/:second_parameter': 'show_page_with_parameter' 

The thing is that I could manage everything with conditions (switch, or if...then):
Eg. If parent page, then parameter is parent_id. But if new_role page, then parameter is role_id. But I already feel as if I am cluttering the router js file.

Is this the right way of doing things, or would you advise me to handle this differently?


Solution

  • I'd get rid of the switch statement and have all of your routes explicitly defined in your routes object -- it's easier to understand and see all routes at a glance.

    routes: {
      '': 'landingPage', 
      'home': 'home', 
      'parents': 'viewParents',
      'parents/:id': 'getParents',
      ...
      '*actions': 'defaultAction' 
    }, 
    

    In addition to that, your handlers are very simple right now, but can change in the future. Most could just use:

    function setView (view, options) {
        app.views.resultView.showView(new view(options));
    }
    

    With some sort of logged-in validation:

    function isLoggedIn() {
      return $.get('php/User/check_session.php').then(function (status) {
        if (status !== 'yes')
          throw new Error('Not logged in');
      });
    }
    

    Or add the log in verification with view setter:

    function setAuthenticatedView (View, options) {
      return function () {
        isLoggedIn().then(function () {
          setView(View, options);
        });
      }
    }
    

    And all together:

    permissionsView: setAuthenticatedView(Permissions_view, {}),
    parentsView: setAuthenticatedView(Parents_view, {}),
    

    This way you have the ability to extend a route with extra functionality without having a giant switch statement, and for simple routes, you can easily read the source and see that, well, these are authenticated views, and they just set a simple backbone view.