问题
I have a project which has an existing database structure and data. Currently project is running on PHP + MySQL and I'm trying to switch from PHP to C# EF 6.0 + MySQL Database first approach.
I have installed NuGet Packages (EF 6.0 and MySQL.Data, MySQL.Web, MySQL.Data.Entity, MySQL.Data.Entities) and modified my app.config according to use MySQL data provider. Up to this state everything works perfectly, I can generate model from database and can insert data on each table without any issue but many-to-many relation tables. I have created 2 dummy tables with name TableA and TableB and the relation table TableA_TableB for requesting help about my issue.
You can see the screen shots of the model generation below:
And the generated model below:
Up to here everything looks fine but as I mentioned when I try to insert a relation between TableA and TableB it fails. You can see my C# code below:
public static void Create()
{
using (MainDataContext mainDataContext = new MainDataContext())
{
try {
mainDataContext.Database.Log = s => System.Diagnostics.Debug.WriteLine(s);
TableA tableA = new TableA();
tableA.Title = "My Title";
tableA.Description = "MyDescription";
mainDataContext.TableA.Add(tableA);
mainDataContext.SaveChanges();
TableB tableB = new TableB();
tableB.Title = "Table B Title";
tableB.Description = "Table B Description";
mainDataContext.TableB.Add(tableB);
mainDataContext.SaveChanges();
tableA.TableB.Add(tableB);
mainDataContext.SaveChanges();
}
catch (Exception ex)
{
}
}
}
The first two of the mainDataContext.SaveChanges(); works fine but the last mainDataContext.SaveChanges(); throws exception (I tried the single transaction it fails too) about FK of my table but after I dig the debug output I faced the exception's real reason. I turn on debug output within my data context and here you can see the output of the insert statements of the EF you can see it below:
Opened connection at 11.1.2016 23:30:46 +02:00 Started transaction at 11.1.2016 23:30:46 +02:00
SET SESSION sql_mode='ANSI';INSERT INTO
TableA
(Title
,Description
) VALUES ( @gp1, @gp2); SELECTID
FROMTableA
WHERE row_count() > 0 ANDID
=last_insert_id() -- @gp1: 'My Title' (Type = String, IsNullable = false, Size = 8) -- @gp2: 'MyDescription' (Type = String, IsNullable = false, Size = 13) -- Executing at 11.1.2016 23:30:47 +02:00 -- Completed in 1 ms with result: EFMySqlDataReaderCommitted transaction at 11.1.2016 23:30:47 +02:00 Closed connection at 11.1.2016 23:30:47 +02:00 Disposed transaction at 11.1.2016 23:30:47 +02:00 Opened connection at 11.1.2016 23:30:55 +02:00 Started transaction at 11.1.2016 23:30:55 +02:00
SET SESSION sql_mode='ANSI';INSERT INTO
TableB
(Title
,Description
) VALUES ( @gp1, @gp2); SELECTID
FROMTableB
WHERE row_count() > 0 ANDID
=last_insert_id()-- @gp1: 'Table B Title' (Type = String, IsNullable = false, Size = 13) -- @gp2: 'Table B Description' (Type = String, IsNullable = false, Size = 19) -- Executing at 11.1.2016 23:30:55 +02:00 -- Completed in 6 ms with result: EFMySqlDataReader
Committed transaction at 11.1.2016 23:30:55 +02:00 Closed connection at 11.1.2016 23:30:55 +02:00 Disposed transaction at 11.1.2016 23:30:55 +02:00 Opened connection at 11.1.2016 23:30:58 +02:00 Started transaction at 11.1.2016 23:30:58 +02:00
INSERT INTO (SELECT
TableA_TableB
.TableAID
,TableA_TableB
.TableBID
FROMTableA_TableB
ASTableA_TableB
)(TableAID
,TableBID
) VALUES ( 1, 1)-- Executing at 11.1.2016 23:30:58 +02:00
-- Failed in 3 ms with error: You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near '(SELECT
TableA_TableB
.TableAID
,TableA_TableB
.TableBID
FROM `TableA_Tab' at line 1Closed connection at 11.1.2016 23:30:58 +02:00 Disposed transaction at 11.1.2016 23:30:58 +02:00 Exception thrown: 'System.Data.Entity.Infrastructure.DbUpdateException' in EntityFramework.dll
Also my table's DDLs below:
CREATE TABLE `TableA` (
`ID` int(10) unsigned NOT NULL AUTO_INCREMENT,
`Title` varchar(255) COLLATE utf8_unicode_ci DEFAULT NULL,
`Description` varchar(255) COLLATE utf8_unicode_ci DEFAULT NULL,
PRIMARY KEY (`ID`)
) ENGINE=InnoDB AUTO_INCREMENT=2 DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci;
CREATE TABLE `TableB` (
`ID` int(10) unsigned NOT NULL AUTO_INCREMENT,
`Title` varchar(255) COLLATE utf8_unicode_ci DEFAULT NULL,
`Description` varchar(255) COLLATE utf8_unicode_ci DEFAULT NULL,
PRIMARY KEY (`ID`)
) ENGINE=InnoDB AUTO_INCREMENT=2 DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci;
CREATE TABLE `TableA_TableB` (
`TableAID` int(10) unsigned NOT NULL,
`TableBID` int(10) unsigned NOT NULL,
KEY `TableA_TableB_TableAID` (`TableAID`),
KEY `TableA_TableB_TableBID` (`TableBID`),
CONSTRAINT `TableA_TableB_TableAID` FOREIGN KEY (`TableAID`) REFERENCES `TableA` (`ID`) ON DELETE CASCADE ON UPDATE CASCADE,
CONSTRAINT `TableA_TableB_TableBID` FOREIGN KEY (`TableBID`) REFERENCES `TableB` (`ID`) ON DELETE CASCADE ON UPDATE CASCADE
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci;
I wonder if this is a bug or I'm doing something wrong does anyone have any idea for my issue ?
Thanks in advance!
回答1:
The problem was about the missing PK on my relation table TableA_TableB after adding PK (TableAID,TableBID) the problem solved. Additionally using uint on EF causes single save issue (you can save tables one by one and after getting ID's you can create relations)
来源:https://stackoverflow.com/questions/34731866/entity-framework-ef6-mysql-database-first-model-many-to-many-relationship-wr