Asp.net core 将返回的属性替换为通过Id链接的不同模型中的另一个属性

Asp.net core 将返回的属性替换为通过Id链接的不同模型中的另一个属性,asp.net-core,entity-framework-core,asp.net-core-webapi,asp.net-core-3.0,Asp.net Core,Entity Framework Core,Asp.net Core Webapi,Asp.net Core 3.0,嗨,我不太确定怎么做 我有一个.NetCore EntityFrame控制器,它可以获取字符列表 当我通过以下操作简单地获取字符列表时,它会起作用: return await _context.Character.ToListAsync(); 这将返回数据库中每个角色的名称、类别、种族、年龄、armorPoints、生命值和spiritAnimalId 但是现在,我想返回动物的真实名称,而不是简单地返回灵兽 所以我开始写一些代码,但很快就失去了计算如何返回灵兽名称的能力 以下是我所拥有的:

嗨,我不太确定怎么做

我有一个.NetCore EntityFrame控制器,它可以获取字符列表

当我通过以下操作简单地获取字符列表时,它会起作用:

return await _context.Character.ToListAsync();
这将返回数据库中每个角色的名称、类别、种族、年龄、armorPoints、生命值和spiritAnimalId

但是现在,我想返回动物的真实名称,而不是简单地返回灵兽

所以我开始写一些代码,但很快就失去了计算如何返回灵兽名称的能力

以下是我所拥有的:

    // GET: api/Characters
    [HttpGet]
    public async Task<ActionResult<IEnumerable<Character>>> GetCharacters()
    {

        var characters= await _context.Character.ToListAsync();

        foreach(Character c in characters)
        {
            var a = _context.SpiritAnimal.FindAsync(c.spiritAnimalId);
            var name = a.Result.Name;
        }
        return charcters;
    }
因此,我不知道如何返回项目列表并用名称替换spiritAnimalId

新代码:

    // GET: api/Characters
    [HttpGet]
    public async Task<ActionResult<List<Character>>> GetCharacters()
    {
         var characters = await _context.Character
                       .Select(x => new
                       {
                           x.Id,
                           x.Name,
                           x.Race,
                           x.Class,
                           x.Age,
                           SpiritAnimalName = x.SpiritAnimalName.Name
                        })
                       .ToListAsync();

        return characters;
    }
新错误:

Cannot implicitly convert type 'System.Collections.Generic.List<<anonymous type
to 'Microsoft.AspNetCore.Mvc.ActionResult<System.Collections.Generic.List

谢谢

如果您还没有,您的角色类上应该有一个导航属性,如:

public SpiritAnimal SpiritAnimal { get; set; }
然后,在进行查询时,应包括此关系,以便将其加入到同一查询中:

var characters = await _context.Character.Include(x => x.SpiritAnimal).ToListAsync();
在迭代字符时,只需访问:character.SpiritAnimal.Name。如果只想从查询中返回名称,则需要使用“选择”将其投影到另一个类或匿名对象中:

var characters = await _context.Character
    .Select(x => new
    {
        CharacterName = x.Name,
        SpiritAnimalName = x.SpiritAnimal.Name
    }
    .ToListAsync();

当Select表达式使用相关实体上的属性时,不需要显式加载它;EF足够聪明,可以意识到它需要进行连接才能满足返回要求。

您好,谢谢,所以我尝试了,并添加了所有字符属性和spirtAnimalName,但出于某种原因,我尝试返回“characters”,它告诉我它无法隐式地将类型Generic.List转换为ActionResult。那么我需要创建一个新类型吗?感谢您尝试直接返回列表,返回类型为ActionResult。如果您在ASP.NET Core 2.1+中使用API控制器,并且返回类型是通用ActionResult,那么您可以这样做。否则,或者如果返回类型为IActionResult,则必须将其包装为结果,如通过Okcharacters。我正在使用netcore 3.1并尝试返回“async Task”。所以我应该返回一个IEnumerable?谢谢。你的问题是协方差。ActionResult的类型param是不变的。因为您告诉它期望IEnumerable,所以您必须实际返回IEnumerable,而不仅仅是实现它的东西,比如List。然而,IEnumerable在这里没有任何好处,因为它已经实现了。只需返回task您正在尝试将匿名类型作为其他类型返回。我在回答中给你的是为了便于解释,因为你没有提供太多关于你正在使用的类型的信息。但是,如果您想像这样重新构造数据,那么您应该真正创建一个视图模型/DTO类,然后使用该类通过Select投影到中并返回。