Budibase/budibase · error · Error
Junction table already exists, cannot create another relatio
Error message
Junction table already exists, cannot create another relationship.
What it means
When saving a many-to-many relationship for external datasources, save() generates a junction table. If a table with the same generated junction name already exists in the datasource, creating another would collide, so it throws. This prevents duplicate/ambiguous join tables.
Source
Thrown at packages/server/src/sdk/workspace/tables/external/index.ts:206
}
const schemaTableId = schema.tableId
const relatedTable = Object.values(tables).find(
table => table._id === schemaTableId
)
if (!relatedTable) {
continue
}
const relatedColumnName = schema.fieldName!
const relationType = schema.relationshipType
if (relationType === RelationshipType.MANY_TO_MANY) {
const junctionTable = generateManyLinkSchema(
datasource,
schema,
tableToSave,
relatedTable
)
if (tables[junctionTable.name]) {
throw new Error(
"Junction table already exists, cannot create another relationship."
)
}
tables[junctionTable.name] = junctionTable
extraTablesToUpdate.push(junctionTable)
} else {
const fkTable =
relationType === RelationshipType.ONE_TO_MANY
? tableToSave
: relatedTable
const foreignKey = generateLinkSchema(
schema,
tableToSave,
relatedTable,
relationType
)
if (fkTable.schema[foreignKey] != null) {
throw new Error(View on GitHub (pinned to a81a902e9a)
Solutions
- Remove or rename the existing junction table relationship before adding the new one
- Change the column/table names so the generated junction table name is unique
- Drop the stale junction table in the connected database and refresh the datasource entities
- Recreate the relationship once, avoiding repeated saves that re-create it
Example fix
// before
"users": { manyToMany: "user_groups" } // junction user_groups_users already exists
// after
delete stale junction relationship, then
"users": { manyToMany: "memberships" } // unique junction name generated Defensive patterns
Strategy: validation
Validate before calling
const junctionName = generateJunctionTableName(column, table, relatedTable)
const entities = await tables.external.getExternalTablesInDatasource(datasourceId)
if (entities[junctionName]) throw new Error(`Junction ${junctionName} already exists`) Type guard
function junctionAvailable(entities: Record<string, Table>, name: string): boolean {
return entities[name] == null
} Try / catch
try {
await tables.external.save(datasourceId, table)
} catch (err) {
if (err.message.includes("Junction table already exists")) {
// reuse existing relationship or drop the junction table first
}
} Prevention
- Check for existing relationships before re-adding many-to-many columns
- Avoid duplicate relationship definitions between the same table pair
- Refresh datasource entities after manual DB changes
When it happens
Trigger: Adding a many-to-many column whose generated junction table name (from table names + column names) matches an existing table in the datasource, then calling save().
Common situations: Two relationships between the same pair of tables producing identical junction names; re-running a migration that already created the junction table; renaming columns so generated names collide.
Related errors
- Unable to generate foreign key - column ${foreignKey} alread
- Unable to generate many link schema, "${noPrimaryName}" does
- Junction table not specified for many-to-many relationship b
- Junction table '${relationship.junctionTable}' not found in
- Table ID is unknown, cannot find table
AI-assisted analysis of Budibase/budibase@a81a902e9a (2026-08-29).
Data as JSON: /api/errors/8ec149b29ea97503.
Report an issue: GitHub.