admin管理员组

文章数量:1325380

I have a use case where a Singleton object has an asynchronous step as part of its initialization. Other public methods of this singleton depend on an instance variable that the initialization step sets up. How would I go about making an async call synchronous?

var mySingleton = (function () {

  var instance;

  function init() {

    // Private methods and variables
    function privateMethod(){
      console.log( "I am private" );
    }

    var privateAsync = (function(){
      // async call which returns an object
    })();

    return {

      // Public methods and variables

      publicMethod: function () {
        console.log( "The public can see me!" );
      },

      publicProperty: "I am also public",

      getPrivateValue: function() {
        return privateAsync;
      }
    };
  };

  return {

    // Get the Singleton instance if one exists
    // or create one if it doesn't
    getInstance: function () {

      if ( !instance ) {
        instance = init();
      }

      return instance;
    }

  };

})();

var foo = mySingleton.getInstance().getPrivateValue();

I have a use case where a Singleton object has an asynchronous step as part of its initialization. Other public methods of this singleton depend on an instance variable that the initialization step sets up. How would I go about making an async call synchronous?

var mySingleton = (function () {

  var instance;

  function init() {

    // Private methods and variables
    function privateMethod(){
      console.log( "I am private" );
    }

    var privateAsync = (function(){
      // async call which returns an object
    })();

    return {

      // Public methods and variables

      publicMethod: function () {
        console.log( "The public can see me!" );
      },

      publicProperty: "I am also public",

      getPrivateValue: function() {
        return privateAsync;
      }
    };
  };

  return {

    // Get the Singleton instance if one exists
    // or create one if it doesn't
    getInstance: function () {

      if ( !instance ) {
        instance = init();
      }

      return instance;
    }

  };

})();

var foo = mySingleton.getInstance().getPrivateValue();
Share Improve this question asked Sep 18, 2016 at 1:16 johnborgesjohnborges 2,56321 silver badges35 bronze badges 8
  • How would I go about making an async call synchronous? - that's unpossible – Jaromanda X Commented Sep 18, 2016 at 1:21
  • What is expected result of var foo = mySingleton.getInstance().getPrivateValue()? – guest271314 Commented Sep 18, 2016 at 1:28
  • This is just a plicated version of how you can't return from an asynchronous method, and boy did you plicate something inherently simple. – adeneo Commented Sep 18, 2016 at 1:30
  • 1 Disclaimer: Singletons are awful. Do not use them, they don't solve anything - just use a regular object and pass it around. The methods of that object should return a promise which can chain the initialization step. – Benjamin Gruenbaum Commented Sep 18, 2016 at 8:54
  • @BenjaminGruenbaum, I'll probably try something like this. Thanks. As I I was coding, this pattern seemed kinda overkill anyway. – johnborges Commented Sep 18, 2016 at 13:07
 |  Show 3 more ments

1 Answer 1

Reset to default 4

If you really want to use an IIFE to create a somewhat singleton-like approach, you still have to use promises or callbacks with async calls, and work with them, not try to convert asynchronous to synchronous

Something like

var mySingleton = (function() {

  var instance;

  function init() {
    // Private methods and variables
    function privateMethod() {
      console.log("I am private");
    }

    var privateAsync = new Promise(function(resolve, reject) {
          // async call which returns an object
        // resolve or reject based on result of async call here
    });

    return {
      // Public methods and variables
      publicMethod: function() {
        console.log("The public can see me!");
      },
      publicProperty: "I am also public",
      getPrivateValue: function() {
        return privateAsync;
      }
    };
  };

  return {

    // Get the Singleton instance if one exists
    // or create one if it doesn't
    getInstance: function() {

      if (!instance) {
        instance = init();
      }

      return instance;
    }

  };

})();

var foo = mySingleton.getInstance().getPrivateValue().then(function(result) {
   // woohoo
}).catch(function(err) {
    // epic fail
})

本文标签: javascriptSingleton with async initializationStack Overflow