Hacktoberfest 2026:维护者为十月标记出来的 issue,仍然开放、适合新手。 浏览 Hacktoberfest issue

BuildAdapter().AdaptToType<T>() does not include all expected properties when source is using inheritance

未关闭
#776 6 条评论 0 个 reaction 已指派 0 人 在 GitHub 查看

还没有人认领这个 Issue。

评估

难度
3/5
预计耗时
1-2 天
新手友好度
45/100
Issue 类型
缺陷
描述清晰度
基本清楚
活跃度
停滞
技术栈
csharp
领域
backend

调研方向

首先使用控制台示例重现 Adapt() 和 BuildAdapter().AdaptToType() 之间的差异,尤其是使用 IMyInterface 和 MyImplementation 的 AdaptToTypeWithInterface。跟踪 BuildAdapter().AdaptToType() 入口点,并将其对源类型的处理与 Adapt() 进行比较;当继承的实现属性在同步和异步路径中都被复制时,即表示完成。

由索引模型根据 Issue 内容生成。

描述

bug configuration problem waiting for info

While rewriting some code to use the async implementation of adapt using package Mapster.Async v2.0.1, I stubled upon an issue where not all expected source properties were copied to the result class.
However, the code was working as expected when I was using .Adapt<T>().

I've tracked it down to the source class being inherited from a base class and using a method where the parameter is of this base class type.
The following code can be used (e.g. in a console application) to reproduce the issue and show the difference in behavior between .Adapt<T>() and AdaptToType<T>():

using Mapster;
using Newtonsoft.Json;

namespace MapsterBug
{
    internal class Program
    {
        static void Main(string[] args)
        {
            // sample source object
            var myImplementation = new MyImplementation
            {
                InterfaceProperty = 123,
                FirstImplementationProperty = 789,
                SecondImplementationProperty = "test"
            };

            // adapt using .Adapt<T>(): the result is as expected
            var resultAdapt = myImplementation.Adapt<MyDto>();

            Console.WriteLine("Result of myImplementation.Adapt<MyDto>():");
            Console.WriteLine(JsonConvert.SerializeObject(resultAdapt, Formatting.Indented));
            Console.WriteLine("\r\n-----------------------------------------\r\n");

            // adapt using .AdaptToType<T>(): the result is as expected
            var resultAdaptToType = myImplementation.BuildAdapter().AdaptToType<MyDto>();

            Console.WriteLine("Result of myImplementation.BuildAdapter().AdaptToType<MyDto>():");
            Console.WriteLine(JsonConvert.SerializeObject(resultAdaptToType, Formatting.Indented));
            Console.WriteLine("\r\n-----------------------------------------\r\n");

            // adapt using .Adapt<T>() inside a method where the parameter is of the interface type: the result is as expected
            var resultAdaptWithInterface = AdaptWithInterface(myImplementation);

            Console.WriteLine("Result of myImplementation.Adapt<MyDto>() in method with interface:");
            Console.WriteLine(JsonConvert.SerializeObject(resultAdaptWithInterface, Formatting.Indented));
            Console.WriteLine("\r\n-----------------------------------------\r\n");

            // adapt using .AdaptToType<T>() inside a method where the parameter is of the interface type:
            // the result only includes the interface property, but it does not include the properties of the implementation
            var resultAdaptToTypeWithInterface = AdaptToTypeWithInterface(myImplementation);

            Console.WriteLine("Result of myInterface.BuildAdapter().AdaptToType<MyDto>() in method with interface:");
            Console.WriteLine(JsonConvert.SerializeObject(resultAdaptToTypeWithInterface, Formatting.Indented));
        }

        static MyDto AdaptWithInterface(IMyInterface myInterface) => myInterface.Adapt<MyDto>();
        static MyDto AdaptToTypeWithInterface(IMyInterface myInterface) => myInterface.BuildAdapter().AdaptToType<MyDto>();
    }

    public interface IMyInterface
    {
        public int InterfaceProperty { get; set; }
    }

    public class MyImplementation : IMyInterface
    {
        public int InterfaceProperty { get; set; }
        public int FirstImplementationProperty { get; set; }
        public string SecondImplementationProperty { get; set; }
    }

    public class MyDto
    {
        public int InterfaceProperty { get; set; }
        public int FirstImplementationProperty { get; set; }
        public string SecondImplementationProperty { get; set; }
    }
}

This code is using AdaptToType<T>() to not complicate things by using an additional package (Mapster.Async), but the AdaptToTypeAsync<T>() method has the same behavior.
When running the application, the output is as follows:

Result of myImplementation.Adapt<MyDto>():
{
  "InterfaceProperty": 123,
  "FirstImplementationProperty": 789,
  "SecondImplementationProperty": "test"
}

-----------------------------------------

Result of myImplementation.BuildAdapter().AdaptToType<MyDto>():
{
  "InterfaceProperty": 123,
  "FirstImplementationProperty": 789,
  "SecondImplementationProperty": "test"
}

-----------------------------------------

Result of myImplementation.Adapt<MyDto>() in method with interface:
{
  "InterfaceProperty": 123,
  "FirstImplementationProperty": 789,
  "SecondImplementationProperty": "test"
}

-----------------------------------------

Result of myInterface.BuildAdapter().AdaptToType<MyDto>() in method with interface:
{
  "InterfaceProperty": 123,
  **"FirstImplementationProperty": 0,**
  **"SecondImplementationProperty": null**
}

Results 1, 2 and 3 are as expected, but the last result only includes the IMyInterface property (InterfaceProperty) and not the additional MyImplementation properties (FirstImplementationProperty and SecondImplementationProperty) marked in bold.

Versions used in code sample:

  • .NET 8
  • Mapster 7.4.0
  • Newtonsoft.Json 13.0.3
主要语言
C#
星标
5.2k
派生
411
平均合并
1 天 8 小时
30 天内合并 PR
4

环境准备

  • 没有 Dockerfile 或 Docker Compose 文件
  • 没有 Pull Request 模板
  • 阅读贡献指南

从这里开始

  1. 先读完整个 Issue,再读项目的贡献指南。
  2. 在 Issue 下留言说明你要接手 —— 这能避免两个人做同样的事。
  3. Fork 仓库,在一个分支上完成修改。
  4. 提交 Pull Request,并在描述里引用这个 Issue 编号。

MapsterMapper/Mapster 的其他 Issue

查看 MapsterMapper/Mapster 的全部 Issue

相似的 Issue

更多 C# Issue

把新 issue 发到你的邮箱

精选适合新手参与的 GitHub issue 摘要。