在 ASP.NET Core Web API 控制器中使用 C# 7 元组 [英] Using a C# 7 tuple in an ASP.NET Core Web API Controller

查看:23
本文介绍了在 ASP.NET Core Web API 控制器中使用 C# 7 元组的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

你知道为什么会这样吗:

Do you know why this works:

public struct UserNameAndPassword
{
    public string username;
    public string password;
}


[HttpPost]
public IActionResult Create([FromBody]UserNameAndPassword usernameAndPassword)
{
    Console.WriteLine(usernameAndPassword);
    if (this.AuthenticationService.IsValidUserAndPasswordCombination(usernameAndPassword.username, usernameAndPassword.password))
        return new ObjectResult(GenerateToken(usernameAndPassword.username));
    return BadRequest();
}

但是当我用元组替换它时,这不起作用?

But when I replace it with a tuple, this doesn’t work?

[HttpPost]
public IActionResult Create([FromBody](string username, string password) usernameAndPassword) //encrypt password?
{
    Console.WriteLine(usernameAndPassword);
    if (this.AuthenticationService.IsValidUserAndPasswordCombination(usernameAndPassword.username, usernameAndPassword.password))
        return new ObjectResult(GenerateToken(usernameAndPassword.username));
    return BadRequest();
}

usernameAndPassword.username.password 都为空.

不允许在控制器中使用元组吗?

Are you not allowed to use tuples in a controller?

推荐答案

它不起作用,因为命名元组名称不太真实",它主要是编译器提供的语法糖.如果您查看表示命名元组的 ValueTuple 类型集,您将看到它们具有诸如 Item1Item2 等属性

It doesn't work because named tuple names are not quite "real", it's mostly syntax sugar provided by compiler. If you look at ValueTuple set of types, by which named tuples are represented, you will see that they have properties like Item1, Item2 and so on.

编译器会将您对命名元组名称的所有引用重写为它们的真实名称(Item1 等).例如你有这个:

Compiler will rewrite all your references to named tuple names to their real names (Item1 etc). For example you have this:

static void Create((string username, string password) usernameAndPassword) {
    Console.WriteLine(usernameAndPassword.username);
    Console.WriteLine(usernameAndPassword.password);
}

但是当您编译它时,您真正将拥有的是:

But when you compile that, what you really will have is this:

static void Create([TupleElementNames(new string[] {"username", "password"})] ValueTuple<string, string> usernameAndPassword)
{
  Console.WriteLine(usernameAndPassword.Item1);
  Console.WriteLine(usernameAndPassword.Item2);
}

你的名字现在只在元数据属性TupleElementNames中,但不在代码中.

Your names are now only in metadata attribute TupleElementNames, but not in code.

因此,当您发布以下内容时:

For that reason, when you post something like:

{"username": "x", "password": "y"}

你的行为,asp.net 无法绑定.但如果你要发帖:

to your action, asp.net cannot bind. But if you would post:

{"item1": "x", "item2": "y"}

那么它将毫无问题地绑定.您可能可以编写自定义绑定器,它可以使用 TupleElementNames 属性,但没有理由真的这样做.只需按照评论中的建议使用单独的参数或真实模型.你的动作输入参数不是一次性的东西.您稍后可能想要验证它们,从模型生成文档等等.

then it will bind with no problems. You can write custom binder probably, which can use TupleElementNames attribute, but there is no reason to really. Just use separate parameters or real model as suggested in comments. Your action input parameters is not some throwaway thing. You might later want to validate them, generate documentation from the model and so on.

这篇关于在 ASP.NET Core Web API 控制器中使用 C# 7 元组的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆