'TypeError: require(...) is not a function while Using sequalize with node js

I am beginner in web dev and trying to create a Full stack project using Mysql Express React Node js. Facing this TypeError issue while using Sequalize with node js. I'm new to this and I can't understand the problem. Can someone please explain it to me and help me find a solution? (PS: If you guys need any other file let me know)

server js

const express = require("express");
const bodyParser = require("body-parser");
const cors = require("cors");

const app = express();

var corsOptions = {
  origin: "http://localhost:8081"
};

app.use(cors(corsOptions));

// parse requests of content-type - application/json
app.use(bodyParser.json());

// parse requests of content-type - application/x-www-form-urlencoded
app.use(bodyParser.urlencoded({ extended: true }));

const db = require("./models");

db.sequelize.sync({ force: true }).then(() => {
  console.log("Drop and re-sync db.");
});

// simple route
app.get("/", (req, res) => {
  res.json({ message: "Welcome." });
});


require("./src/routes/routes")(app);
// set port, listen for requests
const PORT = process.env.PORT || 3000;
app.listen(PORT, () => {
  console.log(`Server is running on port ${PORT}.`);
});

index js

const dbConfig = require("../config/db.config.js");

const Sequelize = require("sequelize");
const sequelize = new Sequelize(dbConfig.DB, dbConfig.USER, dbConfig.PASSWORD, {
  host: dbConfig.HOST,
  dialect: dbConfig.dialect,
  operatorsAliases: false,

  pool: {
    max: dbConfig.pool.max,
    min: dbConfig.pool.min,
    acquire: dbConfig.pool.acquire,
    idle: dbConfig.pool.idle
  }
});

const db = {};

db.Sequelize = Sequelize;
db.sequelize = sequelize;

db.devices = require("./devices.js")(sequelize, Sequelize);

module.exports = db;

devices js


module.exports = (sequelize, Sequelize) => {
    const Device = sequelize.define("devices", {
      serialno: {
        type: Sequelize.INTEGER
      },
      brand: {
        type: Sequelize.STRING
      },
    modelname: {
        type: Sequelize.STRING
      }
    });
  
    return Device;
  };

error

db.devices = require("./devices.js")(sequelize, Sequelize);
                                    ^
TypeError: require(...) is not a function
    at Object.<anonymous> (C:\Users\theta\Documents\project\src\models\index.js:22:37)
    at Module._compile (internal/modules/cjs/loader.js:1138:30)
    at Object.Module._extensions..js (internal/modules/cjs/loader.js:1158:10)
    at Module.load (internal/modules/cjs/loader.js:986:32)
    at Function.Module._load (internal/modules/cjs/loader.js:879:14)
    at Module.require (internal/modules/cjs/loader.js:1026:19)
    at require (internal/modules/cjs/helpers.js:72:18)
    at Object.<anonymous> (C:\Users\theta\Documents\project\src\server.js:19:12)
    at Module._compile (internal/modules/cjs/loader.js:1138:30)
    at Object.Module._extensions..js (internal/modules/cjs/loader.js:1158:10)


Solution 1:[1]

Try to change this on index.js:

db.devices = require("./devices.js")(sequelize, Sequelize);

To this:

const path = require('path')

db.devices = require(path.join(__dirname, 'devices'))(sequelize, Sequelize);

Here's what works for me in TypeScript (using sequelize version 6.17.0):

config.ts

import { Sequelize } from 'sequelize'

const dbName = 'test-db'
const dbUser = 'test-user'
const dbPass = '123123'
const dbHost = 'some-host'

// new Sequelize(name, user, password, options)
export const sequelize = new Sequelize(dbName, dbUser, dbPass, {
  host: dbHost,
  dialect: 'postgres',
  port: 3306,
  dialectOptions: {
    multipleStatements: true,
  },
  pool: {
    max: 5,
    min: 0,
    idle: 10000,
  },
  logging: false,
})

Let's say we have a models/ folder with three files: User.ts, Member.ts and index.ts.

models/User.ts ? we must use module.exports here

module.exports = (sequelize: any, DataTypes: any) => {
  const User = sequelize.define(
    'user',
    {
      id: {
        type: DataTypes.UUID,
        defaultValue: DataTypes.UUIDV4,
        allowNull: false,
        primaryKey: true,
      },
      email: {
        type: DataTypes.STRING(250),
        allowNull: false,
        unique: true,
      },
      password: {
        type: DataTypes.STRING,
        allowNull: true,
        defaultValue: null,
      },
    },
    {
      timestamps: true,
      underscored: true,
      tableName: 'user',
      indexes: [{ unique: true, fields: ['email'] }],
    }
  )

  User.associate = (models: any) => {
    User.hasOne(models.Member, { as: 'Member', foreignKey: 'id' })
  }

  return User
}

models/index.ts

import fs from 'fs'
import path from 'path'
import Sequelize from 'sequelize'
import { sequelize } from './config.js'

// current file basename
const basename = path.basename(__filename)

// our db object
const db: any = {}

// so we don't reload unecessarily
let loaded = false 

const createModels = () => {
  // if already loaded, return cached object
  if (loaded) return db 

  // create an array of model files' basenames
  const filenames = fs.readdirSync(__dirname).filter((file: string) => {
    return (
      // filter out the current `index.ts` file
      file.indexOf('.') !== 0 && file !== basename && file.slice(-3) === '.ts'
    )
  })

  filenames.map((file: any) => {
    // use `require` to load our models
    const model = require(path.join(__dirname, file))(
      sequelize,
      Sequelize.DataTypes
    )
    db[model.name] = model
  })

  // run `.associate` if applicable
  Object.keys(db).map((model) => {
    if (db[model].associate) {
      db[model].associate(db)
    }
  })
  
  // attach both our instance and Sequelize to our db object
  db.sequelize = sequelize
  db.Sequelize = Sequelize

  loaded = true

  return db
}

export default createModels()

export { createModels }

Let me know how it goes.

Solution 2:[2]

If you are tying to import any file for example a font file, then create a mockFile that just have

// mockFile.ts or mockFile.js
export default {};

and then in jest.config.js

  moduleNameMapper: {
    '^.+\\.(woff2)$': '<rootDir>/<path to file>/mockFile.ts',
  },

This will resolve to the mockFil when it will try to import a font file. You can also add other file extentions like '^.+\\.(jpg|png|woff2)$: '<rootDir>/<path to file>/mockFile.ts'.

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1
Solution 2 Aamir Iqubal