【问题标题】:Sequelize.js,How to insert a model with one to many to many relationshipSequelize.js,如何插入具有一对多关系的模型
【发布时间】:2019-08-25 16:41:11
【问题描述】:

我正在使用sequlize.js创建一个一对多的模型,它可以工作,但是我想创建一个一对多的模型,我不知道从哪里开始

现在我已经定义了三个模型,下面是它们的关系

  1. 项目
Projects.associate = () => {
    Projects.Colors = Projects.hasMany(ProjectColors, { foreignKey: 'project_id', sourceKey: 'id' });
  };
  1. 项目颜色
ProjectColors.associate = () => {
    Projects.Sizes = ProjectColors.hasMany(ProjectSizes, { foreignKey: 'project_color_id', sourceKey: 'id' });
  };
  1. 项目大小

有一个对象,我想通过项目模型创建

const project = {
  name: 'xxproject',
  colors:[
    {
      color: 'red',
      sizes:[
        {size: 'L'}
      ]
    },
    {
      color: 'bule',
      sizes:[
        {size: 'L'},
        {size: 'M'}
      ]
    },
  ]
}

我尝试了像Office Document这样的一对多,它可以很好地工作

await Projects.create(project, {
  include: [ Projects.Colors ],
});

如果我更改代码,它会出错

await Projects.create(project, {
      include: [{
        model: Projects.Colors,
      }],
    });

这是错误堆栈

2019-04-04 10:57:10,074 ERROR 60510 [-/127.0.0.1/-/20ms POST /api/v1/projects] nodejs.TypeError: self._expandAttributes is not a function
    at Function._conformOptions (/Users/jaytam/school/garment-production-backend/node_modules/sequelize/lib/model.js:198:12)
    at Function._conformInclude (/Users/jaytam/school/garment-production-backend/node_modules/sequelize/lib/model.js:264:12)
    at options.include.options.include.map.include (/Users/jaytam/school/garment-production-backend/node_modules/sequelize/lib/model.js:213:59)
    at Array.map (<anonymous>)
    at Function._conformOptions (/Users/jaytam/school/garment-production-backend/node_modules/sequelize/lib/model.js:213:39)
    at new Model (/Users/jaytam/school/garment-production-backend/node_modules/sequelize/lib/model.js:3070:24)
    at new projects (/Users/jaytam/school/garment-production-backend/node_modules/sequelize/lib/sequelize.js:340:19)
    at Function.build (/Users/jaytam/school/garment-production-backend/node_modules/sequelize/lib/model.js:1966:12)
    at Function.create (/Users/jaytam/school/garment-production-backend/node_modules/sequelize/lib/model.js:2017:17)
    at ProjectController.create (/Users/jaytam/school/garment-production-backend/app/controller/projects.js:42:20)
    at Object.callFn (/Users/jaytam/school/garment-production-backend/node_modules/egg-core/lib/utils/index.js:44:21)
    at Object.classControllerMiddleware (/Users/jaytam/school/garment-production-backend/node_modules/egg-core/lib/loader/mixin/controller.js:87:20)
    at Object.callFn (/Users/jaytam/school/garment-production-backend/node_modules/@eggjs/router/lib/utils.js:12:21)
    at wrappedController (/Users/jaytam/school/garment-production-backend/node_modules/@eggjs/router/lib/egg_router.js:322:18)
    at dispatch (/Users/jaytam/school/garment-production-backend/node_modules/@eggjs/router/node_modules/koa-compose/index.js:44:32)
    at next (/Users/jaytam/school/garment-production-backend/node_modules/@eggjs/router/node_modules/koa-compose/index.js:45:18)
    at /Users/jaytam/school/garment-production-backend/node_modules/@eggjs/router/lib/router.js:190:18
    at dispatch (/Users/jaytam/school/garment-production-backend/node_modules/@eggjs/router/node_modules/koa-compose/index.js:44:32)
    at /Users/jaytam/school/garment-production-backend/node_modules/@eggjs/router/node_modules/koa-compose/index.js:36:12
    at dispatch (/Users/jaytam/school/garment-production-backend/node_modules/@eggjs/router/lib/router.js:195:33)
    at dispatch (/Users/jaytam/school/garment-production-backend/node_modules/koa-compose/index.js:42:32)
    at /Users/jaytam/school/garment-production-backend/app/middleware/handleGetInt.js:22:11

其实我也想这样写,但是上面的代码不行

await Projects.create(project, {
      include: [{
        model: Projects.Colors,
        include: [{
          model: Projects.Sizes,
        }],
      }],
    });

Travis Haby 建议后,我重试

我模仿 Sequlize.js 文件,改变三个关系定义

Projects.Colors = app.model.ProjectColors.belongsTo(Projects, { foreignKey: 'project_id', targetKey: 'id' });
app.model.ProjectColors.Sizes = app.model.ProjectColors.hasMany(app.model.ProjectSizes, { foreignKey: 'project_color_id', sourceKey: 'id' });

创建代码

await Projects.create(project, {
      association: Projects.Colors,
      include: [ ProjectColors.Sizes ],
});

    await Projects.create(project, {
      include: [{
        association: Projects.Colors,
        include: [{
          association: ProjectColors.Sizes,
        }],
      }],
    })

两种方式只创建项目,每种方式都没有创建颜色和大小

[2019-04-04 14:22:15.564] [cfork:master:60831] worker:60969 exit (code: 0, exitedAfterDisconnect: true, state: dead, isDead: true, isExpected: true, worker.disableRefork: false)
{ name: 'sadqw',
  cycle: 230,
  fund: 1230123,
  manage_by: 'dsa',
  project_colors: [ { color: 'asd', imageUrl: '', project_sizes: [Array] } ],
  status: '0' }
2019-04-04 14:26:24,276 INFO 60980 [egg-sequelize](1ms) Executed (default): INSERT INTO `projects` (`id`,`name`,`cycle`,`fund`,`manage_by`,`created_at`,`updated_at`,`status`) VALUES (DEFAULT,'sadqw',230,1230123,'dsa','2019-04-04 06:26:24','2019-04-04 06:26:24','0');

【问题讨论】:

    标签: javascript sequelize.js


    【解决方案1】:

    我再试一次,效果很好。谢谢@Sagi Rika 和@Travis Haby

    其实就是这么简单

    Projects.associate = () => {
        Projects.Colors = Projects.hasMany(ProjectColors, { foreignKey: 'project_id', sourceKey: 'id' });
      };
    
    ProjectColors.associate = () => {
        Projects.Sizes = ProjectColors.hasMany(ProjectSizes, { foreignKey: 'project_color_id', sourceKey: 'id' });
      };
    

    并调用create方法如下

        Projects.create(project, {
          include: [{
            association: Projects.Colors,
            include: [{
              association: Projects.Sizes,
            }],
          }],
        })
    

    【讨论】:

      【解决方案2】:

      首先,尝试将 projectColors 关联更改为此(假设您收到 models 作为参数):

      ProjectColors.associate = () => {
          ProjectColors.Sizes = ProjectColors.hasMany(models.project_size, { foreignKey: 'project_color_id', sourceKey: 'id' });
          ProjectColors.Projects = ProjectColors.belongsTo(models.project)
      };
      

      其次,尝试添加到 ProjectSizes:

      ProjectSizes.associate = () => {
          ProjectSizes.Colors = ProjectSizes.belongsTo(models.project_color, { foreignKey: 'project_color_id'});
      };
      

      注意:模型名称(在models. 之后使用)是模型定义中定义的名称 (Sequelize.define([modelname])。

      如果有帮助,请告诉我。

      我相信创建应该是这样的:

      await Projects.create(project, {
            include: [{
              association: Projects.Colors,
              include: [ ProjectColors.Sizes ]
            }]
          });
      

      【讨论】:

      • Projects.Colors 。从未定义,你可以在这里使用吗?
      • 如果你在任何模型定义之外,你应该写Projects.Colors而不是models.project.Colors。如果您发布模型定义,我将能够为您提供帮助,但是当我不知道模型名称时,这很难。
      【解决方案3】:

      根据this part of the sequelize docs,您应该能够嵌套如下(取决于您使用的sequelize 的版本):

      return Projects.create(project, {
        include: [{
          association: Projects.Colors,
          include: [ Colors.Sizes ]
        }]
      });
      

      乍一看,您似乎有Projects.Colors,然后是Projects.Sizes,但我认为应该是Colors.Sizes,因为这是多对多的关系。

      希望有帮助!

      【讨论】:

        猜你喜欢
        • 2016-10-15
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2013-01-12
        • 1970-01-01
        • 2021-12-21
        • 2014-09-16
        相关资源
        最近更新 更多