【问题标题】:How to Map (using AutoMapper) entities that have a ForeignKey in ASP.NET CORE 3.1.1 (C#,EntityFrameworkCore)如何在 ASP.NET CORE 3.1.1 (C#,EntityFrameworkCore) 中映射(使用 AutoMapper)具有 ForeignKey 的实体
【发布时间】:2020-07-15 15:44:02
【问题描述】:

我的控制器中有这个函数可以创建一个实体:

    [HttpPost]
    [ProducesResponseType(typeof(ConnectionDBResponse), StatusCodes.Status201Created)]
    [ProducesResponseType(StatusCodes.Status400BadRequest)]
    public async Task<ActionResult<ConnectionDBResponse>> PostConnectionDB([FromBody] CreateConnectionDBQuery query)
    {
        var connectionDBs = _mapper.Map<ConnectionDBDataModel>(query);
        _context.ConnectionDB.Add(connectionDBs);
        await _context.SaveChangesAsync();

        var connectionDBResponse = _mapper.Map<ConnectionDBResponse>(connectionDBs);
        return CreatedAtAction(nameof(GetAllConnectionDB), new { id = connectionDBs.Id }, connectionDBResponse);
    }

为此,我在这两个类之间进行映射: 响应类:

public class CreateConnectionDBQuery
{
    public string ServerType { get; set; }
    public string ServerName { get; set; }
    public string port { get; set; }
    public string AuthType { get; set; }
    public string UserName { get; set; }
    public string Password { get; set; }
    public string DBName { get; set; }
    public string FolderName { get; set; }
    public ScheduleConfigResponse ScheduleConfig { get; set; }
    public Boolean hasEmails { get; set; }
    public EmailConfigResponse EmailConfig { get; set; }
}

public class CreateScheduleConfigQuery
{
    public string HourOfSave { get; set; }
    public int NumDaysInDB { get; set; }
    public CreateConnectionDBQuery ConnDB { get; set; }
    public int ConnDBForeignKey { get; set; }
}

public class CreateEmailConfigQuery
{
    public string SuccesEmail { get; set; }
    public string FailureEmail { get; set; }
    public CreateConnectionDBQuery ConnDB { get; set; }
    public int ConnDBForeignKey { get; set; }
}

还有dataModel类:

[Table("ConnectionDB")]
public class ConnectionDBDataModel
{
    [Key]
    public int Id { get; set; }
    [Required]
    public string ServerType { get; set; }
    [Required]
    public string ServerName { get; set; }
    public string port { get; set; }
    public string AuthType { get; set; }
    public string UserName { get; set; }
    public string Password { get; set; }
    [Required]
    public string DBName { get; set; }
    [Required]
    public string FolderName { get; set; }
    public ScheduleConfigDataModel ScheduleConfig { get; set; }
    public Boolean hasEmails { get; set; }
    public EmailConfigDataModel EmailConfig { get; set; }
}

[Table("ScheduleConfig")]
public class ScheduleConfigDataModel
{
    [Key]
    public int Id { get; set; }
    public string HourOfSave { get; set; }
    public int NumDaysInDB { get; set; }

    public int ConnDBForeignKey { get; set; }
    public ConnectionDBDataModel ConnDB { get; set; }
}

[Table("EmailConfig")]
public class EmailConfigDataModel
{
    [Key]
    public int Id { get; set; }
    public string SuccesEmail { get; set; }
    public string FailureEmail { get; set; }

    public int ConnDBForeignKey { get; set; }
    public ConnectionDBDataModel ConnDB { get; set; }
}

为此,我使用 AutoMapper 如下:

        #region ConnectionDB

        CreateMap<ConnectionDBDataModel, ConnectionDBResponse>();

        CreateMap<CreateConnectionDBQuery, ConnectionDBDataModel>()
            .ForMember(dest => dest.Id, opt => opt.Ignore());

        CreateMap<UpdateConnectionDBQuery, ConnectionDBDataModel>()
            .ForMember(dest => dest.Id, opt => opt.Ignore());

        #endregion

        #region ScheduleConfig

        CreateMap<ScheduleConfigDataModel, ScheduleConfigResponse>()
            .ForMember(dest => dest.ConnDBForeignKey, opt => opt.Ignore());

        CreateMap<CreateScheduleConfigQuery, ScheduleConfigDataModel>()
            .ForMember(dest => dest.Id, opt => opt.Ignore())
            .ForMember(dest => dest.ConnDBForeignKey, opt => opt.Ignore());

        CreateMap<UpdateScheduleConfigQuery, ScheduleConfigDataModel>()
            .ForMember(dest => dest.Id, opt => opt.Ignore());

        #endregion ScheduleConfig

        #region EmailConfig

        CreateMap<EmailConfigDataModel, EmailConfigResponse>()
            .ForMember(dest => dest.ConnDBForeignKey, opt => opt.Ignore());

        CreateMap<CreateEmailConfigQuery, EmailConfigDataModel>()
            .ForMember(dest => dest.Id, opt => opt.Ignore())
            .ForMember(dest => dest.ConnDBForeignKey, opt => opt.Ignore());

        CreateMap<UpdateEmailConfigQuery, EmailConfigDataModel>()
            .ForMember(dest => dest.Id, opt => opt.Ignore());

        #endregion

但是当我尝试创建这个元素时,它给了我一个错误,说它来自一个无效的映射,如下面的屏幕所示:

我尝试使用以下代码行忽略外键(因为我猜这个问题来自外键):.ForMember(dest =&gt; dest.ConnDBForeignKey, opt =&gt; opt.Ignore());,但我想这不是解决该问题的方法。 任何帮助将不胜感激!

【问题讨论】:

  • 映射错误来自CreateConnectionDBQuery 类。你能用它代替ConnectionDBResponse 类吗?
  • 是的,我现在要编辑问题
  • 你能添加一个ScheduleConfigResponse 类吗?

标签: c# asp.net-core entity-framework-core automapper


【解决方案1】:

发生错误是因为在将CreateConnectionDBQuery 映射到ConnectionDBDataModel 时,没有为ScheduleConfig 属性的类型定义映射。

我猜在您的CreateConnectionDBQuery 中,您的ScheduleConfig 属性应该是CreateScheduleConfigQuery 类型而不是ScheduleConfigResponse

或者,如果您不想更改模型,您可以添加从ScheduleConfigResponseScheduleConfigDataModel 的映射配置。但这似乎不太直观。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2012-08-31
    • 1970-01-01
    • 2017-11-12
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2022-08-18
    相关资源
    最近更新 更多