1

我有一个从 Postgres 移植到 MySQL 的应用程序。别管为什么。该应用程序使用 Entity Framework 4 来查询数据库。

由于各种原因,我不得不Guids在我的 C# 代码中使用,将它们保存到数据库中,然后根据保存的Guids. 我对 MySQL 以及它如何处理本质上是 blob 的东西不是很熟悉。

首先,MySQL 中没有 UUID 类型。我必须将它们保存为 BINARY(16) 值。好的。我已将列创建为 BINARY(16) 并将数据写入表中。好的。

我的问题是我看不到与 Guid 的存储值相匹配。我编写了一个单元测试,它Guid使用表已知的数据写入数据,然后尝试检索它。数据很好地进入数据库,但是当我尝试读回它时,我没有得到任何行。

这是一个示例表架构:

CREATE TABLE `MyDatabase`.`MyTable` (
    `id`                INT             NOT NULL AUTO_INCREMENT,
    `guid`              BINARY(16)      NOT NULL,
    `applicationId`     INT(11)         NOT NULL,
    `name`              VARCHAR(256)    NOT NULL,
    Description         VARCHAR(256)    NULL,
    SessionTimeout      INT             NOT NULL,
    DomainId            INT             NOT NULL,
    PRIMARY KEY (`id`),
    CONSTRAINT IX_aspnetx_groups UNIQUE ( `applicationId`, `id` )
);

这是实体框架代码:

var g = ( from r in context.MyTable
          where r.guid = id
          select r ).Single();

这是 Entity Framework 生成的查询:

SELECT
`Extent1`.`id`, 
`Extent1`.`guid`, 
`Extent1`.`applicationId`, 
`Extent1`.`name`, 
`Extent1`.`Description`, 
`Extent1`.`SessionTimeout`, 
`Extent1`.`DomainId`
FROM `aspnetx_groups` AS `Extent1`
WHERE `Extent1`.`guid` = '81d7de5e-4212-4ff8-b3d4-9f115261971d' LIMIT 2;

当它执行时,它不返回任何行,导致在我的 C# 代码中引发“序列不包含元素”异常。

我该如何进行这项工作?

4

3 回答 3

1

事实证明,我遇到的问题与 MySQL Connector/Net 包中实体框架连接器的怪癖有关。如果您将其BINARY(16)用作数据库中的数据类型,则需要添加一个连接字符串设置Guids

Old Guids=True

将其添加到连接字符串后,Entity Framework 开始发出在插入、更新或比较 Guid 时真正有效的代码。

我还得出结论,MySQL 中的 UUID / Guid 支持只是半生不熟,需要一些认真的工作才能使其达到可用状态。

于 2012-08-13T20:38:43.210 回答
1

在 SELECT 的 WHERE 子句中,看起来您正在将 BINARY(16)(等号左侧的 guid)与右侧的字符串文字进行比较。

为了进行有效的比较,我将该字符串文字转换为 BINARY(16),然后将其与 guid 进行比较。

因此,删除所有短划线字符,然后使用 UNHEX 函数应该可以解决问题:

WHERE `Extent1`.`guid` = 
  UNHEX(REPLACE('81d7de5e-4212-4ff8-b3d4-9f115261971d','-',''))

为了提高性能,您希望您的查询引用左侧的裸 guid 列(就像它一样),而不是将 guid 列包装在任何类型的函数中。您会希望在谓词的文字端进行任何转换,这样转换只需在查询开始时进行一次,而不必对表中的每一行进行转换。

于 2012-08-09T20:36:07.670 回答
0

只是为了补充托尼的答案,我一直在使用旧的 guid,直到今天,EF 似乎没有正确转换 GUID。

它以某种方式解析了错误的 GUID,因此在代码级别比较这些值时我必须使用不同的 GUID

于 2021-12-17T03:37:20.673 回答