Search code examples
javascriptsemantics

Shorthand creation of object chains in Javascript


What I am interested to know is if there is a shorter way of achieving the following:

App.Plugins = App.Plugins || {};
App.Plugins.SomePlugin = App.Plugins.SomePlugin || {};
App.Plugins.SomePlugin.Models = App.Plugins.SomePlugin.Models || {};
App.Plugins.SomePlugin.Views = App.Plugins.SomePlugin.Views || {};
App.Plugins.SomePlugin.Collections = App.Plugins.SomePlugin.Collections || {};

As far as I know, this format is fine, please someone let me know if I'm mistaken, I'm just wondering if there is some nicer way of doing this initial setup on my singleton.

Thanks in advance...


Solution

  • I don't understand exactly why you do this

    Anyway a shorter way to write that is:

    App={
     Plugins:{
      SomePlugin:{
       Models:{},
       Views:{},
       Collections:{}
      }
     }
    }
    

    then considering the function

    function defaults(obj, prop) {
        return obj[prop] = obj[prop] || {};
    }
    

    would return an error using

    defaults(App.Plugins.AnotherPlugin,'Models')
    

    checking this is a pain:

    var x={};
    if(App&&
       App.Plugins&&
       App.Plugins.AnotherPlugin&&
       App.Plugins.AnotherPlugin.Models
    ){
     x=App.Plugins.AnotherPlugin.Models
    }
    console.log(x);
    

    A solution is

    var x={};
    try{x=App.Plugins.AnotherPlugin.Models}catch(e){}
    console.log(x)
    

    this gives you no errors

    but you can't set it the easy way.

    EDIT

    comment answer

    Then you should start checking at the point where nothing is certain. In your case you just need to check if anotherPlugin exists.you probably already have App & App.Plugins.so you don't need App=App||{}, but only App.Plugins.AnotherPlugin

    !App.Plugins.AnotherPlugin||App.Plugins.AnotherPlugin=NewPlugin
    

    or a function

    function addPlugin(name,newPlugin){
     !App.Plugins[name]||App.Plugins[name]=newPlugin
    }
    

    An define your own standards... I mean why return an object if it does not exist?

    if it does not exist you can't do anything anyway.

    and again the biggest problem is always to check if it exists... and like i already described above it is try catch.

    EDIT2

    check this function.

    function def(a,b,c,d){
     c=b.split('.');
     d=c.shift();
     a[d]||(a[d]={});
     !(c.length>0)||def(a[d],c.join('.'));
    }
    

    usage:

    var A={};
    def(A,'B.C.D.E.F')
    //this transforms your {}
    //to 
    A:{
     B:{
      C:{
       D:{
        E:{
         F:{
         }
        }
       }
      }
     }
    }
    

    http://jsfiddle.net/5NgWL/

    to create your plugin:

    var App={}
    def(App,'Plugins.SomePlugin.Models')
    def(App.Plugins.SomePlugin,'View')
    // &/or
    def(App,'Plugins.SomePlugin.Collections')