You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

指定insertGraph中列仅插入不更新,解决未允许关联报错问题

Fixing 'trying to upsert an unallowed relation' with Objection.js insertGraph

Let's break down your problem and walk through the solutions step by step:

1. Fix the Invalid allowInsert Syntax

First, your current allowInsert syntax is incorrect—this is likely the root cause of the unallowed relation error. Objection.js requires specific formatting to target nested relation columns. You have two valid options:

Option A: Dot Notation

Use dot syntax to reference nested columns directly:

ModelName.query(trx)
  .allowInsert([
    'subrelation2.columnToPopulate1',
    'subrelation2.columnToPopulate2'
  ])
  .insertGraph(data);

Option B: Object Syntax (More Readable for Nested Relations)

Use an object to explicitly define allowed columns per relation:

ModelName.query(trx)
  .allowInsert({
    subrelation2: ['columnToPopulate1', 'columnToPopulate2']
  })
  .insertGraph(data);

By fixing this syntax, you're telling Objection.js that the subrelation2 relation is permitted for insertion, along with the specific columns you want to populate.

2. Let Objection.js Handle the Foreign Key Automatically

You don't need to include or allow the foreign key column (foreignId) in your allowInsert configuration. When inserting nested relations via insertGraph, Objection.js automatically sets the foreign key value to match the parent record's ID—assuming your model relations are properly defined (e.g., belongsTo, hasMany).

  • Remove the foreign key from your input data: Don't include foreignId in the data object you pass to insertGraph.
  • Don't add it to allowInsert: Let Objection manage this column internally to avoid conflicts.

3. Implement Insert-Only Columns (Prevent Upserts for Specific Columns)

If you want certain columns to be populated only on insert (not updated during upserts), you'll need to separate insert and upsert permissions using allowInsert and allowUpsert, then configure the onConflict behavior:

Example with UpsertGraph

ModelName.query(trx)
  // Allow all desired columns for insert
  .allowInsert({
    subrelation2: ['columnToPopulate1', 'columnToPopulate2', 'insertOnlyColumn']
  })
  // Exclude insert-only columns from updates
  .allowUpsert({
    subrelation2: ['columnToPopulate1', 'columnToPopulate2']
  })
  .upsertGraph(data, {
    onConflict: (builder) => {
      builder.onConflict('id') // Replace with your unique constraint
        .doUpdateSet((updateBuilder) => {
          // Only update columns allowed in allowUpsert
          updateBuilder.set('columnToPopulate1', updateBuilder.ref('excluded.columnToPopulate1'))
                       .set('columnToPopulate2', updateBuilder.ref('excluded.columnToPopulate2'));
        });
    }
  });

This ensures that insertOnlyColumn is only set when creating new records, and ignored when updating existing ones.

Key Notes

  • Double-check your model relations: Ensure the parent-child relationship is correctly defined (e.g., belongsTo in the child model pointing to the parent) so Objection can auto-manage the foreign key.
  • Avoid using relation2.* unless necessary: Your goal to retain integrity checks is valid—using explicit column lists prevents accidental overwrites of sensitive or auto-managed columns.

内容的提问来源于stack exchange,提问作者IdiakosE Sunday

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.13 07:47:24