In node.js is there a way to reuse a list of const-require statements, in all files?

79 Views Asked by At

In a node project I will have these 20 lines of code ...

const db = require('./db')
const comms = require('./comms')
const stuff = require('./stuff')
const blah = require('./blah')
const bleh = require('./bleh')
...
const admin = require('./admin')

And I literally paste those 20 lines at the top of each and every one of the 20 .js files in question.

You do this for simple procedural efficiency (any of the lines unused, in that file, VS will harmlessly indicate it's unused, but you never have a missing one, and everyone on the team does the same thing, and you never have to think about it).

{Actually, one team I was on someone wrote a line of script to automate the process! It would just make the top of each file the same, based on all the current files. But setting that solution aside:}

Is there some way to keep those 20 lines in another file reqs.js (or reqs.txt, or something) and have it "applied" to all files?

So it would be something like

actuallyRunTheCodeFrom( 'reqs.js' )

or something like

macro( someMacro )

which literally inserts the 20 lines of code in question, "in", this file.

I appreciate I could require reqs.js, and then prepend "reqs." everywhere, that is not what I am asking, thanks.

I believe there is no way to "dynamically const" in node; there's nothing like ['db', 'comms', 'stuff'].foreach(const $0 = require(./$0)). If I'm wrong, pls tell me.

Anyway to do this?


The @YoushaAleayoub method!

https://www.mediafire.com/file/t81fppv2x6wnwty/ya.zip/file

it works perfectly BUT unfortunately it does produce a mass of warnings

enter image description here

Also note for the record. With the "y.a. method" you do have to "change the line at the top of each file" each time someone on the team adds or deletes a file. eg

 const { aa, bb, cc } = require('./common.js')

becomes

 const { aa, bb, cc, dd } = require('./common.js')

When a new file is added, they all need to be changed.

(Ideally, I was wondering if there is some sort of "macro like include" - the answer seems to be no.)

Here are the files to copy/paste:

ya % ls
aa.js       bb.js       cc.js       common.js
ya % tail -n +1 *js
==> aa.js <==
// aa.js
const { aa, bb, cc } = require('./common.js')

function sayOne() { console.log(1) }
function sayTwo() { console.log(2) }

console.log("test")
console.log("testB")
bb.sayOne()
console.log("testC")
cc.sayOne()

module.exports = { sayOne, sayTwo }
==> bb.js <==
// bb.js
const { aa, bb, cc } = require('./common.js')

function sayOne() { console.log(10) }
function sayTwo() { console.log(20) }

module.exports = { sayOne, sayTwo }

==> cc.js <==
// cc.js
const { aa, bb, cc } = require('./common.js')

function sayOne() { console.log(100) }
function sayTwo() { console.log(200) }

module.exports = { sayOne, sayTwo }

==> common.js <==
// common.js
const aa = require('./aa')
const bb = require('./bb')
const cc = require('./cc')
module.exports = { aa, bb, cc }

Simple method

https://www.mediafire.com/file/u3f6o1n7jf5pz95/usual.zip/file

If you tediously paste the N "const lines" at the top of every file (i.e. the whole point of this question is to avoid having to do that), as you can see it works fine with no warnings.

To copy/paste:

% ls
aa.js   bb.js   cc.js
% tail -n +1 *js              
==> aa.js <==
// aa.js

const aa = require('./aa')
const bb = require('./bb')
const cc = require('./cc')

function sayOne() { console.log(1) }
function sayTwo() { console.log(2) }

console.log("test")
console.log("testB")
bb.sayOne()
console.log("testC")
cc.sayOne()

exports.sayOne = sayOne
exports.sayTwo = sayTwo
==> bb.js <==
// bb.js

const aa = require('./aa')
const bb = require('./bb')
const cc = require('./cc')

function sayOne() { console.log(10) }
function sayTwo() { console.log(20) }

exports.sayOne = sayOne
exports.sayTwo = sayTwo

==> cc.js <==
// cc.js

const aa = require('./aa')
const bb = require('./bb')
const cc = require('./cc')

function sayOne() { console.log(100) }
function sayTwo() { console.log(200) }

exports.sayOne = sayOne
exports.sayTwo = sayTwo

As I say, I was basically wondering if there is some sort of "macro like include" in node.js - the answer seems to be no sadly!

2

There are 2 best solutions below

4
Mike 'Pomax' Kamermans On BEST ANSWER

Use an aggregator file and then import from there. For example, let's create a collection of files we need imported "everywhere":

first, a.js exporting a function

function aFunction() {
  return `a`;
}

module.exports = { aFunction };

then, b.js exporting a normal const

const B_CONST = `b`;

module.exports = { B_CONST };

then, c.js exporting a symbol

const cSymbol = Symbol(`c`);

module.exports = { cSymbol };

And finally a d.js that exports a class

class D {
  constructor() {
    this.d = `d`;
  }
}

module.exports = { D };

We can aggregate those in an imports.js that re-export them as a single collection:

const a = require("./a.js");
const b = require("./b.js");
const c = require("./c.js");
const d = require("./d.js");

module.exports = { a, b, c, d };

Which we can now import in any file that needs it. Let's create an index.js:

const { a, b, c, d } = require("./imports.js");

console.log(a.aFunction);
console.log(b.B_CONST);
console.log(c.cSymbol);
console.log(d.D);

And then let's run that:

$node index.js
[Function: aFunction]
b
Symbol(c)
[class D]

And if you want to skip the namespace and instead directly export a single specific thing, then just do that, and then have the aggregator export it as part of the collection too.

For instance, let's add an e.js that directly exports just a function, rather than wrapping it in its own namespace:

function verifyData() {};
module.exports = verifyData;

Cool. We simply update our imports.js:

...
const verifyData = require("e.js");
module.exports = { a, b, c, d, verifyData };

As well as our index.js:

const {a, b, c, d, verifyData } = require("./imports.js");
...
console.log(verifyData);

And we're done:

$node index.js
[Function: aFunction]
b
Symbol(c)
[class D]
[Function: verifyData]
2
Yousha Aleayoub On

If I got it correctly:

Simply create a file named common.js where you define your common statements:

// common.js file
const fs = require('fs');
const http = require('http');
// Add more common statements as needed.
module.exports = { fs, http };

Then in your other files, import the common.js file:

// myapp.js file
const { fs, http, example } = require('./common.js');
// Now you can use fs and http and example in this file.