3gwebtrain
3gwebtrain

Reputation: 15303

Is it possible to call one function from another? (keeping separate files)

I understand I can call any file at any time to call its functions (please correct me if I am wrong). I decided to test this by creating two modules (one and two), and calling function nested in two, from one. This works, but I'm unable to call function one from function two.

Main.js

requirejs.config({
  baseUrl: "js"
});

require([
  "script/one"
], function ($, $Ui, hBs, one) {
  //works fine
  one.get("I am the initiator");
});

one.js

define(['script/two'], function (two) {
  var one = function () {
    return {
      get: function (msg) {
        //works
        console.log("get: " + msg);
        //works fine    
        two.serve1("I am from one of one");
      },
      post: function (msg) {
        // i am calling this method from two.js
        console.log("post: " + msg);
        two.serve2("i am from two of two");
      }
    }

  }
  return new one;
})

two.js

define([ 'require', 'script/one'], function (require,one) {
  var two = function () {
     one = require('script/one'); // throwing error as "Uncaught Error: Module name "script/one" has not been loaded yet for context: _"
    return {
      serve1: function (msg) {
        console.log("2 in serve1 :" + msg)
        // calling doesn't
        one.post("initiated from one, called in two");
        // throws "Uncaught TypeError: Cannot call method 'post' of undefined"
      },
      serve2: function (msg) {
        console.log("2 in serve2 :" + msg)
      }
    }
  }
  return new two;
})

Why am I getting this error?

Upvotes: 0

Views: 588

Answers (1)

Andreas Köberle
Andreas Köberle

Reputation: 110922

The problem is that you have create a circular dependency.

In that case only one of the injected values have the right value, the other one is just undefined. If you think about, its clear that this cant work, cause how should the one that is injected in the second one should know the second one as he is not created when the first one is created.

Fortunately there is a work around for this. Use the require function to load the dependency later:

define(["require", 'script/one'], function (require, one) {
  var two = function () {
    return {
      serve1: function (msg) {
        one = require('script/one');
        console.log("2 in serve1 :" + msg)
        // calling doesn't
        one.post("initiated from one, called in two");
        // throws "Uncaught TypeError: Cannot call method 'post' of undefined"
      },
      serve2: function (msg) {
        console.log("2 in serve2 :" + msg)
      }
    }
  }
  return new two;
})

Note that you still need the reference to 'script/one' in the dependency array.

Upvotes: 2

Related Questions