Я пытаюсь использовать Sequelize со следующими маршрутами JS API

#node.js #sequelize.js #next.js

#node.js #sequelize.js #next.js

Вопрос:

Я пытаюсь использовать Sequelize со следующими маршрутами JS API… но я падаю почти на первое препятствие.

Что бы я ни делал, я, похоже, не могу импортировать модель в свой route.js досье.

 import nextConnect from 'next-connect'
const {models} = require('../../models')


const handler = nextConnect()
.post(async (req, res) => {
    const { qname, qanswer } = req.body
    const question = await  models.Question.create({ qname, qanswer })
    res.statusCode = 200
    return res.json({ status: 'success' })
})
export default handler
 

Независимо от того, что я пытаюсь и делаю, «модели» всегда не определены. Я довольно новичок в node js, и я подозреваю, что делаю что-то основное неправильно, но, черт возьми, я не знаю, что!

Я считаю, что относительный путь правильный. route.js файл находится по адресу ./Pages/API / route.js и страницы находятся на том же уровне, что и каталог моделей.

Модель, похоже, определена правильно, я использовал команду CLI для построения модели и запуска следующего кода…

 const {sequelize} = require('./models')
async function main(){
    await sequelize.sync({force: true})
}

main()
 

внутри App.js (который находится в корневой папке) успешно построил базу данных, что заставляет меня думать, что я правильно понял этот бит. По сути, я в значительной степени использую код котельной плиты, предоставляемый командой CLI.

Одна вещь, которую я заметил… когда я вызываю конечную точку restful, я вижу следующий отчет JS о следующем…

 warn  - ./Models/index.js
Critical dependency: the request of a dependency is an expression
 

Я подозреваю, что это как-то связано со мной проблема !!!:)

Наконец, я должен сказать, что я пробовал комбинации попыток ИМПОРТА вместо REQUIRE и с фигурными скобками и без них — в отчаянии!

Заранее спасибо за любую помощь…

определение модели приведено ниже на случай, если это полезный контекст..

 'use strict';
const {
  Model
} = require('sequelize');
module.exports = (sequelize, DataTypes) => {
  class Questions extends Model {
    /**
     * Helper method for defining associations.
     * This method is not a part of Sequelize lifecycle.
     * The `models/index` file will call this method automatically.
     */
    static associate(models) {
      // define association here
    }
  };
  Questions.init({
    qname: {
      type: DataTypes.STRING,
      allowNull: false
    },
    qanswer: DataTypes.STRING
  }, {
    sequelize,
    modelName: 'questions',
  });
  return Questions;
};
 

Ответ №1:

Извините, если кто-то потратил время на то, чтобы посмотреть на это. Модель определяется как вопрос s.. Я использовал Вопрос…. Я думаю, что с таким количеством новых вещей, которые нужно обдумать, мне не хватает основ !!:)

Ответ №2:

я понял это! после стольких поисковых подсказок в Google. я не знаю, решили ли вы уже вашу проблему, но я надеюсь, что это поможет другим, кто застрял в той же проблеме.

прежде всего, убедитесь, что ваша модель работает с командой миграции. Я создаю папку и файл sequelize по умолчанию, используя

 npx sequelize-cli init
 

и это моя пользовательская модель, созданная с использованием команды sequelize-cli (имя таблицы в базе данных — «пользователи»)

 // models/users.js
'use strict';
const {
  Model
} = require('sequelize');

module.exports = (sequelize, DataTypes) => {
  class Users extends Model {
    /**
     * Helper method for defining associations.
     * This method is not a part of Sequelize lifecycle.
     * The `models/index` file will call this method automatically.
     */
    static associate(models) {
      // define association here
      this.belongsTo(models.UsersTypes, {
          foreignKey: 'user_type_id',
      });
      
    }
  }
  Users.init({
    id: {
      type: DataTypes.UUID,
      defaultValue: sequelize.fn('uuid_generate_v4'),
      primaryKey: true
    },
    username: {
      type: DataTypes.STRING(35),
      unique: true
    },
    password: DataTypes.STRING,
    last_login: DataTypes.DATE,
    employee_id: DataTypes.INTEGER,
    is_block: DataTypes.BOOLEAN,
    is_active: DataTypes.BOOLEAN
  }, {
    sequelize,
    modelName: 'users',
    timestamps: true,
    createdAt: 'created_at',
    updatedAt: 'updated_at'
  });
  
  return Users;
};
 

затем обновите свой index.js модель (настраиваемая с вашей моделью, я использую пользовательскую модель в качестве примера)

 // models/index.js
'use strict';

const fs = require('fs');
const path = require('path');
const Sequelize = require('sequelize');
const basename = path.basename(__filename);
const env = process.env.NODE_ENV || 'development';
const config = require(__dirname   '/../config/config.js')[env];
const db = {};

const Users = require('./users'); //define your model here

let sequelize;
if (config.use_env_variable) {
  sequelize = new Sequelize(process.env[config.use_env_variable], config);
} else {
  sequelize = new Sequelize(config.database, config.username, config.password, config);
}

fs
  .readdirSync(__dirname)
  .filter(file => {
    return (file.indexOf('.') !== 0) amp;amp; (file !== basename) amp;amp; (file.slice(-3) === '.js');
  })
  .forEach(file => {
    const model = require(path.join(__dirname, file))(sequelize, Sequelize.DataTypes);
    db[model.name] = model;
  });

Object.keys(db).forEach(modelName => {
  if (db[modelName].associate) {
    db[modelName].associate(db);
  }
});

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

db.Users = Users(sequelize, Sequelize); // add this line, without this, not gonna work in next step

module.exports = db;
 

затем в ваших маршрутах api

 'use strict';

import db from '../../../models/index';
db.sequelize.sync();
const Users = db.Users;

export default async function handler(req, res) {

  const {body, headers} = req;
  const {username, password} = body;

  if (!username || !password) {
    return res.status(400).json({"message":"Missing username/password"});
  }

  try {
    await db.sequelize.authenticate();
  } catch (error) {
    return res.status(400).json({"message":"Unable to connect to the database:", error});
  }

  const users = await Users.findAll();      

  res.status(200).json({ users })
}
 

i get the result

 {
    "users": [
        {
            "id": "35479f7c-80aa-480e-9ad9-92262f527b19",
            "username": "yosiazwan",
            "password": "$2a$06$dxmTHstIjAM3.d1.SUE5mey7qnQZ2icYnKmWcboitr6J59LOdZMRW",
            "last_login": null,
            "employee_id": null,
            "is_block": false,
            "is_active": true,
            "created_at": "2022-07-26T07:38:55.874Z",
            "updated_at": "2022-07-26T07:38:55.874Z"
        }
    ]
}
 

я получаю подсказку отсюда
https://techsolutionshere.com/next-js-with-sequelize-and-postgresql /

Редактировать: я нахожу лучшие решения

 // models/index.js
'use strict';

const fs = require('fs');
const path = require('path');
const Sequelize = require('sequelize');
const modelPath = process.cwd()   '/models/'; //add this line
const basename = path.basename(__dirname   '/../models/index.js'); //change this line
const env = process.env.NODE_ENV || 'development';
const config = require(__dirname   '/../config/config.js')[env];

const db = {};

let sequelize;
if (config.use_env_variable) {
  sequelize = new Sequelize(process.env[config.use_env_variable], config);
} else {
  sequelize = new Sequelize(config.database, config.username, config.password, config);
}

fs
  .readdirSync(modelPath) //change this line
  .filter(file => {
    return (file.indexOf('.') !== 0) amp;amp; (file !== basename) amp;amp; (file.slice(-3) === '.js');
  })
  .forEach(file => {
    const model = require(__dirname   '/../models/'   file)(sequelize, Sequelize.DataTypes); //change this line
    db[model.name] = model;
  });

Object.keys(db).forEach(modelName => {
  if (db[modelName].associate) {
    db[modelName].associate(db);
  }
});

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

module.exports = db;
 

объяснение:

 // for fs read absolute path, using "__dirname   '/../models/'" not working
const modelPath = process.cwd()   '/models/'; //add this line

// using __filename as basename not work because will return api route file instead, 
// we need index.js as value
const basename = path.basename(__dirname   '/../models/index.js');

//fs read modelPath
fs
  .readdirSync(modelPath)

// "__dirname   '/../models/'   file" must always insert in require function
// if above value is use as const or other variable not gonna working
const model = require(__dirname   '/../models/'   file)(sequelize, Sequelize.DataTypes);
 

Исправление :

в models/users.js я определяю

 modelName: 'users' 
 

но лучше изменить на

 tableName: 'users' 
 

потому что лучше использовать имя таблицы в нижнем регистре, а имя модели — camelCase