You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用MongoDB.EntityFrameworkCore时ID未更新的问题求助

解决EF MongoDB驱动插入实体后ID未填充的问题

问题原因

你遇到的问题是EF MongoDB驱动默认不会自动将MongoDB生成的_id值回填到实体的ObjectId字段,需要显式配置主键的生成策略,或调整ID字段类型适配驱动的自动回填逻辑。

解决方案一:保留ObjectId类型,配置值生成策略

1. 简化模型类属性配置

移除冗余属性,确保MongoDB的主键标识正确:

internal class Movie
{
    [BsonId]
    [BsonRepresentation(BsonType.ObjectId)]
    public ObjectId _id { get; set; }
    public string title { get; set; }
    public string rated { get; set; }
    public string plot { get; set; }
}

2. 在DbContext中显式配置主键生成规则

在OnModelCreating中添加配置,告诉EF该字段由数据库生成并回填:

protected override void OnModelCreating(ModelBuilder modelBuilder)
{
    base.OnModelCreating(modelBuilder);
    modelBuilder.Entity<Movie>()
        .ToCollection("movies")
        .HasKey(m => m._id);
    
    // 配置ID在插入时自动生成并回填
    modelBuilder.Entity<Movie>()
        .Property(m => m._id)
        .ValueGeneratedOnAdd();
}

解决方案二:将ID改为string类型(更简便适配)

如果无需直接操作ObjectId对象,改为string类型可让驱动自动处理ID生成与回填:

1. 修改模型类

internal class Movie
{
    [BsonId]
    [BsonRepresentation(BsonType.ObjectId)]
    public string Id { get; set; }
    public string title { get; set; }
    public string rated { get; set; }
    public string plot { get; set; }
}

2. 调整DbContext配置(可选)

Id属性会自动映射到MongoDB的_id字段,无需额外配置:

protected override void OnModelCreating(ModelBuilder modelBuilder)
{
    base.OnModelCreating(modelBuilder);
    modelBuilder.Entity<Movie>().ToCollection("movies");
}

验证修改效果

修改后重新运行插入代码,SaveChangesAsync()执行完成后,实体的ID字段会被正确填充为MongoDB生成的ID值:

var test = new Movie()
{
    plot = "test",
    title = "test",
    rated = "test"
};
await db.Movies.AddAsync(test);
await db.SaveChangesAsync();

Console.WriteLine(test.plot + " with id " + test._id); // 若用string类型则改为test.Id

内容的提问来源于stack exchange,提问作者Nick Glas

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.05 07:27:25