Asp.Net Core 2 Web API 500 内部服务器错误
Asp.Net Core 2 Web API 500 internal server error
当我尝试通过 Postman 访问 API 时,
发送:
localhost:5050/api/Auth/token
正文:
{ "UserName": "jouverc", "Password": "P@ssw0rd!" }
此方法:
[Produces("application/json")]
[Route("api/Auth")]
public class AuthController : Controller
{
#region constructor injection
private readonly IPasswordHasher<User> _hasher;
private readonly UserManager<User> _userManager;
private readonly IConfigurationRoot _config;
private readonly SignInManager<User> _signInManager;
public AuthController(IPasswordHasher<User> hasher, UserManager<User> userManager, SignInManager<User> signInManager, IConfigurationRoot config)
{
_hasher = hasher;
_userManager = userManager;
_signInManager = signInManager;
_config = config;
}
#endregion
#region createToken
[HttpPost("token")]
public async Task<IActionResult> CreateToken([FromBody] CredentialModel model)
{
try
{
var user = await _userManager.FindByNameAsync(model.UserName);
if (user != null)
{
if (_hasher.VerifyHashedPassword(user, user.PasswordHash, model.Password) == PasswordVerificationResult.Success)
{
return Ok(CreateToken(user));
}
}
}
catch (Exception)
{
//log
}
return null;
}
private async Task<JwtPacket> CreateToken(User user)
{
var userClaims = await _userManager.GetClaimsAsync(user);
var claims = new[]
{
new Claim(JwtRegisteredClaimNames.Sub, user.UserName),
new Claim(JwtRegisteredClaimNames.Jti,Guid.NewGuid().ToString())
}.Union(userClaims);
var key = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(_config["Tokens:Key"]));
var cred = new SigningCredentials(key, SecurityAlgorithms.HmacSha256);
var token = new JwtSecurityToken(issuer: _config["Tokens:Issuer"],
audience: _config["Tokens:Audience"],
claims: claims,
expires: DateTime.UtcNow.AddDays(2),
signingCredentials: cred
);
return new JwtPacket
{
Token = new JwtSecurityTokenHandler().WriteToken(token),
Expiration = token.ValidTo.ToString(),
UserName = user.UserName
};
}
public class JwtPacket
{
public string Token;
public string UserName;
public string Expiration;
}
#endregion
}
我收到 500 内部服务器错误:
Unable to resolve service for type 'Microsoft.Extensions.Configuration.IConfigurationRoot' while attempting to activate 'WebAPI.Controllers.AuthController
我应该如何配置启动?
public Startup(IConfiguration configuration)
{
Configuration = configuration;
}
public IConfiguration Configuration { get; }
// This method gets called by the runtime. Use this method to add services to the container.
如果您只是从 appsettings.json 中读取值,请改用 IConfiguration 接口。
下面是如何在 Startup 中实现它class
public Startup(IApplicationEnvironment appEnv)
{
var builder = new ConfigurationBuilder()
.SetBasePath(appEnv.ApplicationBasePath)
.AddEnvironmentVariables()
.AddJsonFile("appsettings.json");
Configuration = builder.Build();
}
public IConfigurationRoot Configuration { get; set; }
public void ConfigureServices(IServiceCollection services)
{
services.AddSingleton<IConfiguration>(Configuration);
}
在 .net 核心 2.0 中
IConfigurationRoot
现在只是 IConfiguration
.
本文档中的解释:Migrating from 1.x to 2.0。
在 2.0
个项目中,1.x
个项目固有的样板配置代码运行 behind-the-scenes。例如,环境变量和应用程序设置在启动时加载。等效的 Startup.cs
代码简化为 IConfiguration
使用注入实例初始化:
public Startup(IConfiguration configuration)
{
Configuration = configuration;
}
public IConfiguration Configuration { get; }
只需在控制器的构造函数中将 IConfigurationRoot 更改为 IConfiguration。
但使用 IOpions 模式将设置注入控制器可能会更好。
当我尝试通过 Postman 访问 API 时,
发送:
localhost:5050/api/Auth/token
正文:
{ "UserName": "jouverc", "Password": "P@ssw0rd!" }
此方法:
[Produces("application/json")]
[Route("api/Auth")]
public class AuthController : Controller
{
#region constructor injection
private readonly IPasswordHasher<User> _hasher;
private readonly UserManager<User> _userManager;
private readonly IConfigurationRoot _config;
private readonly SignInManager<User> _signInManager;
public AuthController(IPasswordHasher<User> hasher, UserManager<User> userManager, SignInManager<User> signInManager, IConfigurationRoot config)
{
_hasher = hasher;
_userManager = userManager;
_signInManager = signInManager;
_config = config;
}
#endregion
#region createToken
[HttpPost("token")]
public async Task<IActionResult> CreateToken([FromBody] CredentialModel model)
{
try
{
var user = await _userManager.FindByNameAsync(model.UserName);
if (user != null)
{
if (_hasher.VerifyHashedPassword(user, user.PasswordHash, model.Password) == PasswordVerificationResult.Success)
{
return Ok(CreateToken(user));
}
}
}
catch (Exception)
{
//log
}
return null;
}
private async Task<JwtPacket> CreateToken(User user)
{
var userClaims = await _userManager.GetClaimsAsync(user);
var claims = new[]
{
new Claim(JwtRegisteredClaimNames.Sub, user.UserName),
new Claim(JwtRegisteredClaimNames.Jti,Guid.NewGuid().ToString())
}.Union(userClaims);
var key = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(_config["Tokens:Key"]));
var cred = new SigningCredentials(key, SecurityAlgorithms.HmacSha256);
var token = new JwtSecurityToken(issuer: _config["Tokens:Issuer"],
audience: _config["Tokens:Audience"],
claims: claims,
expires: DateTime.UtcNow.AddDays(2),
signingCredentials: cred
);
return new JwtPacket
{
Token = new JwtSecurityTokenHandler().WriteToken(token),
Expiration = token.ValidTo.ToString(),
UserName = user.UserName
};
}
public class JwtPacket
{
public string Token;
public string UserName;
public string Expiration;
}
#endregion
}
我收到 500 内部服务器错误:
Unable to resolve service for type 'Microsoft.Extensions.Configuration.IConfigurationRoot' while attempting to activate 'WebAPI.Controllers.AuthController
我应该如何配置启动?
public Startup(IConfiguration configuration)
{
Configuration = configuration;
}
public IConfiguration Configuration { get; }
// This method gets called by the runtime. Use this method to add services to the container.
如果您只是从 appsettings.json 中读取值,请改用 IConfiguration 接口。
下面是如何在 Startup 中实现它class
public Startup(IApplicationEnvironment appEnv)
{
var builder = new ConfigurationBuilder()
.SetBasePath(appEnv.ApplicationBasePath)
.AddEnvironmentVariables()
.AddJsonFile("appsettings.json");
Configuration = builder.Build();
}
public IConfigurationRoot Configuration { get; set; }
public void ConfigureServices(IServiceCollection services)
{
services.AddSingleton<IConfiguration>(Configuration);
}
在 .net 核心 2.0 中
IConfigurationRoot
现在只是 IConfiguration
.
本文档中的解释:Migrating from 1.x to 2.0。
在 2.0
个项目中,1.x
个项目固有的样板配置代码运行 behind-the-scenes。例如,环境变量和应用程序设置在启动时加载。等效的 Startup.cs
代码简化为 IConfiguration
使用注入实例初始化:
public Startup(IConfiguration configuration)
{
Configuration = configuration;
}
public IConfiguration Configuration { get; }
只需在控制器的构造函数中将 IConfigurationRoot 更改为 IConfiguration。
但使用 IOpions 模式将设置注入控制器可能会更好。