157

I'm writing a simple server for Node.js and I'm using my own class called User which looks like:

function User(socket) {
    this.socket = socket;
    this.nickname = null;

    /* ... just the typical source code like functions, variables and bugs ... */

    this.write = function(object) {
        this.socket.write(JSON.stringify(object));
    }
};

and then later in the process I'm instantiating it a lot:

var server = net.createServer(function (socket) {
    /* other bugs */
    var user = new User(socket);
    /* more bugs and bad practise */
});

Can I move my User class definition to another javascript file and "include" it somehow?

Paul Rumkin
  • 6,737
  • 2
  • 25
  • 35
martin
  • 93,354
  • 25
  • 191
  • 226

6 Answers6

288

You can simply do this:

user.js

class User {
  //...
}

module.exports = User //  Export class

server.js

const User = require('./user.js')

let user = new User()

This is called CommonJS module.

ES Modules

Since Node.js version 14 it's possible to use ES Modules with CommonJS. Read more about it in the ESM documentation.

user.mjs ( extension is important)

export default class User {}

server.mjs

import User from './user.mjs'

let user = new User()
Paul Rumkin
  • 6,737
  • 2
  • 25
  • 35
  • what if, User had some input parameters, like module.exports = function User(data). Then the var user = new User(); whould have been changed to var user = new User(data);? – C graphics Jan 08 '14 at 21:40
  • Yes. `User` is usual js function. – Paul Rumkin Jan 10 '14 at 10:56
  • 2
    You don't need to create the constant User in server.js. Change the last line of users.js into `module.exports = new User();` This will create a new instance of User each time the module is required. Then you can simply require the module for each variable like this: `let user = require('./user.js');`. – Nadav Dec 25 '17 at 09:26
  • This is incorrect. It will create user instance just once when module is required. – Paul Rumkin Dec 25 '17 at 19:06
  • @Pasha Rumkin what you say is wrong. This answer is correct. – Barnack May 27 '18 at 20:31
  • 1
    @Barnack There are several my answers. Which is wrong and which is correct? – Paul Rumkin Jun 05 '18 at 22:00
  • 1
    @pashaRumkin Instantiate object locally, but I got TypeError: is not a constructor – Md Alamin Dec 20 '18 at 07:17
  • @MdAlamin It's better to create a new question with complete source code to anyone could help you. Anyway could not say something without your code source. – Paul Rumkin Dec 21 '18 at 08:16
16

Using ES6, you can have user.js:

export default class User {
  constructor() {
    ...
  }
}

And then use it in server.js

const User = require('./user.js').default;
const user = new User();
yedidyak
  • 1,964
  • 13
  • 26
  • i get an `SyntaxError: Unexpected token export` when i do as you described... i have node version `v10.16.3` – dcts Mar 06 '20 at 15:57
7

Modify your class definition to read like this:

exports.User = function (socket) {
  ...
};

Then rename the file to user.js. Assuming it's in the root directory of your main script, you can include it like this:

var user = require('./user');
var someUser = new user.User();

That's the quick and dirty version. Read about CommonJS Modules if you'd like to learn more.

sevenflow
  • 767
  • 1
  • 6
  • 21
5

Another way in addition to the ones provided here for ES6

module.exports = class TEST{
    constructor(size) {
        this.map = new MAp();
        this.size = size;

    }

    get(key) {
        return this.map.get(key);
    }

    length() {
        return this.map.size;
    }    

}

and include the same as

var TEST= require('./TEST');
var test = new TEST(1);
Gaurav Rawat
  • 1,294
  • 1
  • 25
  • 52
2

If you append this to user.js:

exports.User = User;

then in server.js you can do:

var userFile = require('./user.js');
var User = userFile.User;

http://nodejs.org/docs/v0.4.10/api/globals.html#require

Another way is:

global.User = User;

then this would be enough in server.js:

require('./user.js');
pimvdb
  • 151,816
  • 78
  • 307
  • 352
0

To build upon Paul Rumkin answer(the first answer), you can use the ES Modules class with the .js extension and don't have to use the.mjs extension.

To do that, make sure you have the package.json file. If you don't have one, run the following command to create it:

npm init -y

Add "type": "module" at the end of your the package.json file:

{
 ...
 "type": "module" 
}

Create user.js file and export a class from it:

export default class User {}

Import the class in server.js:

import User from './user.js'

let user = new User()
Stanley Ulili
  • 702
  • 5
  • 7