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

ASP.NET Core Web API查询MongoDB时返回ObjectId而非Timestamp的方法

问题:MongoDB ObjectId数组序列化/反序列化异常处理

MongoDB用户集合结构

{
    _id: ObjectId("6420eb68cd0df40a33b0ead7"),
    FirstName: 'Ashutosh',
    LastName: 'Garg',
    Email: 'email@id.com',
    Password: 'password',
    Role: 'Tenant',
    Properties: [
        ObjectId("6420eeb8cd0df40a33b0eadb")
    ]
}

ASP.NET Core Web API的User类定义

using MongoDB.Bson;
using MongoDB.Bson.Serialization.Attributes;
using MongoDB.Driver;
using System.Text.Json.Serialization;

namespace webapi.Models
{
    public class User
    {
        [BsonId]
        [BsonRepresentation(BsonType.ObjectId)]
        public String? Id { get; set; }
        public string? FirstName { get; set; }
        public string? LastName { get; set; }
        public string Email { get; set; }
        public string Password { get; set; }
        public string Role { get; set; }
        public List<ObjectId>? Properties { get; set; }
    }
}

问题现象

调用登录接口时,返回的Properties字段显示为包含Timestamp、Machine等信息的完整ObjectId对象,而非期望的字符串格式ObjectId值。尝试将Properties改为string[]类型时,又触发反序列化错误:System.FormatException: 无法从BsonType 'ObjectId'反序列化'String'。

解决方案

1. 自定义ObjectId的JSON转换器

问题核心是System.Text.Json默认会把ObjectId序列化为其内部结构,而非字符串。我们可以写一个自定义转换器,让它在序列化时输出ObjectId的字符串形式,反序列化时把字符串转回ObjectId。

创建转换器类:

using MongoDB.Bson;
using System.Text.Json;
using System.Text.Json.Serialization;

public class ObjectIdJsonConverter : JsonConverter<ObjectId>
{
    public override ObjectId Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options)
    {
        return ObjectId.Parse(reader.GetString()!);
    }

    public override void Write(Utf8JsonWriter writer, ObjectId value, JsonSerializerOptions options)
    {
        writer.WriteStringValue(value.ToString());
    }
}

然后在User类的Properties字段上添加特性,指定使用这个转换器:

[JsonConverter(typeof(ObjectIdJsonConverter))]
public List<ObjectId>? Properties { get; set; }

2. 全局注册转换器(推荐)

如果项目中有多个地方需要处理ObjectId的JSON序列化,可以在Program.cs里全局注册这个转换器,不用每个字段都加特性:

builder.Services.AddControllers()
    .AddJsonOptions(options =>
    {
        options.JsonSerializerOptions.Converters.Add(new ObjectIdJsonConverter());
    });

3. 效果验证

修改完成后,接口返回的Properties字段会变成字符串数组,格式类似["6420eeb8cd0df40a33b0eadb"],同时从MongoDB读取数据时,ObjectId数组也能正常反序列化,不会再出现格式异常。

内容的提问来源于stack exchange,提问作者Ashutosh Garg

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.26 20:15:32