From 05a707a00a7674dfa100455765331ba15e8b1e15 Mon Sep 17 00:00:00 2001 From: Jocelyne Date: Tue, 15 Oct 2024 15:16:51 +0200 Subject: [PATCH] fix: EXPOSED-588 Foreign key error when table has dot in its name When creating a child table that has a dot in its name, the foreign key name created by Exposed would include that dot, which causes an error. The fix is to replace the dot with an underscore when constructing the foreign key name. --- .../org/jetbrains/exposed/sql/Constraints.kt | 2 +- .../tests/sqlite/ForeignKeyConstraintTests.kt | 42 +++++++++++++++++++ 2 files changed, 43 insertions(+), 1 deletion(-) diff --git a/exposed-core/src/main/kotlin/org/jetbrains/exposed/sql/Constraints.kt b/exposed-core/src/main/kotlin/org/jetbrains/exposed/sql/Constraints.kt index 76598f536c..73447e72da 100644 --- a/exposed-core/src/main/kotlin/org/jetbrains/exposed/sql/Constraints.kt +++ b/exposed-core/src/main/kotlin/org/jetbrains/exposed/sql/Constraints.kt @@ -112,7 +112,7 @@ data class ForeignKeyConstraint( val fkName: String get() = tx.db.identifierManager.cutIfNecessaryAndQuote( name ?: ( - "fk_${fromTable.tableNameWithoutSchemeSanitized}_${from.joinToString("_") { it.name }}__" + + "fk_${fromTable.tableNameWithoutSchemeSanitized.replace('.', '_')}_${from.joinToString("_") { it.name }}__" + target.joinToString("_") { it.name } ) ).inProperCase() diff --git a/exposed-tests/src/test/kotlin/org/jetbrains/exposed/sql/tests/sqlite/ForeignKeyConstraintTests.kt b/exposed-tests/src/test/kotlin/org/jetbrains/exposed/sql/tests/sqlite/ForeignKeyConstraintTests.kt index 2c43e4abc8..cf3a65490e 100644 --- a/exposed-tests/src/test/kotlin/org/jetbrains/exposed/sql/tests/sqlite/ForeignKeyConstraintTests.kt +++ b/exposed-tests/src/test/kotlin/org/jetbrains/exposed/sql/tests/sqlite/ForeignKeyConstraintTests.kt @@ -1,5 +1,6 @@ package org.jetbrains.exposed.sql.tests.sqlite +import org.jetbrains.exposed.dao.id.IntIdTable import org.jetbrains.exposed.exceptions.ExposedSQLException import org.jetbrains.exposed.sql.* import org.jetbrains.exposed.sql.SqlExpressionBuilder.eq @@ -10,6 +11,7 @@ import org.jetbrains.exposed.sql.tests.shared.Category import org.jetbrains.exposed.sql.tests.shared.DEFAULT_CATEGORY_ID import org.jetbrains.exposed.sql.tests.shared.Item import org.jetbrains.exposed.sql.tests.shared.assertEquals +import org.jetbrains.exposed.sql.tests.shared.assertTrue import org.jetbrains.exposed.sql.tests.shared.expectException import org.jetbrains.exposed.sql.transactions.transaction import org.junit.Assume @@ -240,4 +242,44 @@ class ForeignKeyConstraintTests : DatabaseTestsBase() { } } } + + @Test + fun testTableWithDotInName() { + withDb { + val q = db.identifierManager.quoteString + val parentTableName = "${q}SOMENAMESPACE.SOMEPARENTTABLE$q" + val childTableName = "${q}SOMENAMESPACE.SOMECHILDTABLE$q" + + val parentTester = object : IntIdTable(parentTableName) { + val text_col = text("parent_text_col") + } + val childTester = object : IntIdTable(childTableName) { + val text_col = text("child_text_col") + val int_col = reference("child_int_col", parentTester.id) + } + + try { + SchemaUtils.create(parentTester) + assertTrue(parentTester.exists()) + SchemaUtils.create(childTester) + assertTrue(childTester.exists()) + + val parentId = parentTester.insertAndGetId { + it[text_col] = "Parent text" + } + val childId = childTester.insertAndGetId { + it[text_col] = "Child text" + it[childTester.int_col] = parentId + } + + parentTester.update({ parentTester.id eq parentId }) { it[text_col] = "Updated parent text" } + + childTester.update({ childTester.id eq childId }) { it[text_col] = "Updated child text" } + childTester.deleteWhere { childTester.id eq childId } + } finally { + SchemaUtils.drop(childTester) + SchemaUtils.drop(parentTester) + } + } + } }