104

I'm getting the error while running the following code in Node.js

var assert = require('assert');
var request = require('request');
var index = require('./index');
it('verify javascript function', function(done) {
    var v2 = index.AddNumbers(5, 6);
    assert.equal(11, v2);
    done();
});

The index.js file contain the following code:

function AddNumbers(a,b){
    return a+b;
}

What am I doing wrong?

hong4rc
  • 3,999
  • 4
  • 21
  • 40
Karthick Gk
  • 1,065
  • 2
  • 8
  • 8
  • I was using a "return statement" outside of the function, in one of my included files. removing it solved the problem. – Hassan Raza Apr 20 '21 at 11:42

13 Answers13

200

This happened to me many times because of circular dependency, check if you have 2 classes that are requiring each other, remove one of them from requiring the other and the issue should be solved

shimi_tap
  • 7,822
  • 5
  • 23
  • 23
  • 1
    Wow.I had to restructure my app because of this error. Thanks a bunch. – Abundance Oshianor Jan 31 '19 at 21:27
  • 1
    I'd been attempting to debug a problem caused by this for a few hours. It was in a utility class which had too many functions in it really. Splitting it up into smaller more logical modules solved the problem, presumably by mitigating an unidentified circular reference. :) – FrugalTPH Jan 08 '20 at 12:26
  • 7
    This is a failure of node in so many ways but, as always, the most important of the failures is the nonsensical and misleading error message. – Nick Apr 02 '20 at 14:44
  • Switched back to JS for a new Node project (Node.js v14.15.0 doesn't support import syntax) and wrongly wrote `exports = function()...` instead of `module.exports = function()...`. – Sufian Feb 27 '21 at 12:51
  • Really wish this was suggested in the circular dependency error better. I removed an unused import from a refactor and that fixed the issue. – Ian Smith Mar 17 '22 at 01:42
  • https://stackoverflow.com/a/70741450/9630323 , it can be solved by importing the function inside the function we are using – Akash NO Jun 02 '22 at 07:03
  • Hi shimi_tap, you are absolutely right. I like your answer and appreciate that. Thanks a lot baby. – Nay Oo Kyaw Jul 28 '22 at 06:56
65

With NodeJS modules, to make something public, you have to export it. Add this to the end of index.js:

module.exports.AddNumbers = AddNumbers;

(That's using the old CommonJS modules. For ESM, it would be export AddNumbers;)


Here it is running on my machine:

$ cat index.js 
function AddNumbers(a,b){
    return a+b;
}

module.exports.AddNumbers = AddNumbers;

$ cat example.js 
var index = require('./index');
var v2 = index.AddNumbers(5,6);
console.log(v2);

$ node example.js
11
T.J. Crowder
  • 1,031,962
  • 187
  • 1,923
  • 1,875
21

I'm fairly a beginner at Node JS so I managed to get this error by importing a function like so:

const { functionName } = require('./function')

instead of like so:

const functionName = require('./function')

Editing my post to add an explanation since I've learned more node since I wrote it. If a module exports an object containing multiple functions functions like so:

module.exports = { functionName, otherFunction }

Then the function has to be deconstructed out of the object during the import, as in the first code snippet. If the module exports a single function or a default function, like so:

 module.exports = functionName

Then tt must be imported directly, as in the second code snippet.

Tanya Branagan
  • 551
  • 1
  • 12
  • 21
9

If you need to expose a specific component, function or a variable to public. You have to exports those components using JavaScript modules.

let add = (a,b)=>{
    return ( a+b);
}
module.exports.add=add;

or if you want to expose multiple functions, you can do as follows.

let add = (a,b)=>{
    return (a+b);
}
let subtract = (a, b)=>{
    return (a-b);
}
module.exports={
   add : add,
   subtract : subtract
};
Aravinda Meewalaarachchi
  • 2,551
  • 1
  • 27
  • 24
6

This is happening because two files are referencing each other i.e You are calling function (s) from file A in file B and vice versa which is called Circular Dependency.

p_zheey
  • 61
  • 1
  • 2
3

Your "AddNumbers" function in the "index.js" file should be as follows,

function AddNumbers(a,b){
    var addition = function(a, b){
      return (a + b) ;
    };

    module.exports = {
       additionResult: addition
    };
}

And you need to call it in your "Node.js" file as follows

var assert = require('assert');
var request = require('request');
var index = require('./index');
it('verify javascript function', function(done) {
    var v2 = index.additionResult(5, 6);
    assert.equal(11, v2);
    done();
});

This should work. Please note that you call the function by whatever the token name you exported the return value by (I use a different name here just for clarity). Almost everybody uses the same name as the function name so there are no confusion. Also in ES6, if you use the same name you can export as just,

module.exports = {
       addition
};

instead of,

module.exports = {
       addition: addition
};

since you use the same name. It is an ES6 feature.

Indunil
  • 31
  • 1
2

I ran into the same problem while trying to follow a Nodejs tutorial by w3schools. I copied the following code from them:

exports.myDateTime = function () {
return Date();
};

That, however, wouldn't work for me. What resolved the problem for me was adding module. before the exports keyword like this:

module.exports.myDateTime = function () {
return Date();
};
Jimmy
  • 864
  • 13
  • 24
1

The most correct answer was from @shimi_tap. I want to reply it as comment, but doesn't have enough reputation, so I am gonna answer it using a simple example, like in this case below:

  1. File A has 3 functions to process database activity: function addDB, updateDB, and delData;
  2. File B has 2 functions to process User activity on smartphone: function addHistory, and editHistory;

Function updateDB in file A is calling function editHis in file B, and function editHistory is calling function updateDB in file A. This is what we called circular-dependency. And we need to prevent it by only giving output of state from editHistory and the rest will be processed inside file A.

//ORIGINAL FUNCTIONS which caused CIRCULAR DEPENDENCY
function updateDB() {
  //process update function here
  //call function in fileB
  const history = require("fileB.js");
  await history.editHistory(data).then((output) => {
    if(output["message"] === "success"){
      response = {
        state: 1,
        message: "success",
      };
    }
  });
  return response; 
}

//THIS is the WRONG ONE
function editHistory() {
  //process function to edit History here
  //call function in fileA
  const file = require("fileA.js");
  await file.updateDB(data).then((output) => { //You should not call it here
    if(output["message"] === "success") {
      output = {
        state: 1,
        message: "success",
      };
    }
  });
  return output; 
}

//==================================================//
//THE FIX
function updateDB() {
  //process function here
  const history = require("fileB.js");
  await history.editHistory(data).then((output) => {
    if(output["message"] === "success"){
      await updateDB(data).then((output) => {
        response = {
          state: 1,
          message: "success",
        };
      });
    } else {
      log("Error");
    }
  });
  return response; 
}

function editHistory() {
  //process function to edit History here
  // No more calling to function inside the file A
  output = {
    state: 1,
    message: "success",
  };
  return output; 
}
Wege
  • 177
  • 2
  • 11
  • Hope this will give a better explanation and example for other newbie developers like me in the future. Good luck coding, guys. – Wege Sep 12 '22 at 09:57
0

https://medium.com/visual-development/how-to-fix-nasty-circular-dependency-issues-once-and-for-all-in-javascript-typescript-a04c987cf0de

this post visualizes the circular dependency injection like a child or nested file tried to import parent or top-level file

repo.js

service.js

there are 2 files

service.js uses repo.js file by importing it works but check in repo.js that it tried to import service.js file it shows circular dependency injection warning

Mohamed MS
  • 51
  • 3
0

In my case the problem was the missing semicolon at the end of the lines.

const codec = JSONCodec()

(async () => {
  for await (const message of subscription) {
    const payload = codec.decode(message.data)
    stompServer.send('/topic/update-event', {}, payload)
  }
})()

This produced the following error:

TypeError: JSONCodec(...) is not a function

I was so used to writing code without semicolons, which led me to this problem with the bare NodeJs. As soon as I had put the semicolons, the problem disappeared.

-1

A simple way I debugged this (After about 2 days of troubleshooting) was to actually see why 'x' is not a function. Basically, console.log(x) to see the actual object returned. Turned out I was conflicting x with another declared variable (happens especially when you use axios.res and req,res args.

Tubostic
  • 11
  • 4
-1

Require the other file in function level.

fileOne.js

function main() {
    const fileTwo = require('./fileTwo');
    console.log("hello from file one");
}
module.exports = main;
main();

fileTwo.js

function main() {
    const fileOne = require('./fileOne');
    console.log("hello from file two");
}

module.exports = main;
main();

Now execute > node fileOne.js

Output:

hello from file two
hello from file one
  • const sample2 = require('./sample2') const sample = async (payload)=>{ const {value}= payload; const response = sample2({sample}); } module.exports = sample enter code here const sample2 = async ({sample})=>{ const response = sample({value}); } – Salman Hameed Jun 11 '21 at 07:30
-2

One silly mistake I did was while exporting was:

module.exports = [module_name_1, module_name_2, ..., module_name_n]

The right way is:

module.exports = {module_name_1, module_name_2, ..., module_name_n}
  • 3
    Your answer seems unrelated to the question – mousetail Aug 31 '20 at 18:13
  • 1
    It might be related: I'm more familiar with front end javascript, but if you export your module definitions incorrectly, when you try to use them you could get a type error described by OP (likely the thing you tried calling is undefined). ANKIT, if this is what you meant, you could add that rationale to your answer. – code11 Aug 31 '20 at 19:11