EF6+PostgreSQL用xmin并发令牌,插入语句含该列的解决方法咨询
解决EF6插入时包含PostgreSQL xmin系统列的问题
方案1:修正EDMX属性配置(优先尝试)
你当前的EDMX配置存在一处关键问题:CSDL部分的Type应对应C#的String而非数据库的text,这可能导致EF无法正确识别该列为数据库生成列。按以下步骤修正:
- 打开EDMX文件的XML视图
- 在SSDL的对应实体
<EntityType>下,确保xmin的<Property>节点配置:<Property Name="xmin" Type="text" Nullable="false" StoreGeneratedPattern="Computed" /> - 修改CSDL部分的
<Property>节点,将Type改为String并保留StoreGeneratedPattern:<Property Name="xmin" Type="String" Nullable="false" StoreGeneratedPattern="Computed" /> - 保存EDMX并重新生成模型类,此时EF会明确该列由数据库生成,插入时不会将其包含在语句中。
方案2:使用EF6命令拦截器(方案1无效时使用)
如果EDMX配置仍未生效,可通过EF6的DbCommandInterceptor拦截插入命令,手动移除xmin相关的SQL片段:
- 创建拦截器类:
public class XminInsertInterceptor : DbCommandInterceptor { public override void NonQueryExecuting(DbCommand command, DbCommandInterceptionContext<int> interceptionContext) { if (command.CommandText.StartsWith("INSERT", StringComparison.OrdinalIgnoreCase)) { // 移除INSERT字段列表中的xmin var fieldRegex = new Regex(@"\b(xmin\s*,?\s*)", RegexOptions.IgnoreCase); command.CommandText = fieldRegex.Replace(command.CommandText, string.Empty); // 移除对应参数及VALUES中的占位符 var xminParam = command.Parameters.Cast<DbParameter>() .FirstOrDefault(p => p.ParameterName.IndexOf("xmin", StringComparison.OrdinalIgnoreCase) >= 0); if (xminParam != null) { command.Parameters.Remove(xminParam); // 调整VALUES段的占位符 var valuesSplit = command.CommandText.Split(new[] { "VALUES" }, StringSplitOptions.None); if (valuesSplit.Length == 2) { var paramList = valuesSplit[1].Trim('(', ')').Split(',') .Select(p => p.Trim()).Where(p => p != xminParam.ParameterName).ToList(); command.CommandText = $"{valuesSplit[0]}VALUES({string.Join(", ", paramList)})"; } } } base.NonQueryExecuting(command, interceptionContext); } } - 在你的DbContext静态构造函数中注册拦截器:
static YourDbContext() { DbInterception.Add(new XminInsertInterceptor()); }
方案3:修改T4模板避免模型覆盖(可选)
数据库优先模式下,每次更新模型会覆盖手动添加的特性,可修改模型对应的.tt模板,自动为xmin属性添加数据库生成特性:
- 打开模型的
.tt文件,找到生成属性的代码段 - 在生成属性前添加判断逻辑:
这样每次生成模型类时,xmin属性都会自动带上该特性,强化EF对其的认知。if (property.Name == "xmin") { WriteLine(" [DatabaseGenerated(DatabaseGeneratedOption.Computed)]"); }
内容的提问来源于stack exchange,提问作者eXPerience
相关产品推荐
相关产品推荐

