我有一个ASP.NET核心项目,我正try 在其中使用依赖项注入. 然而,我得到了这个例外:

模型绑定的复杂类型不能是抽象类型或值类型,并且必须具有无参数构造函数.记录类型必须有一个主构造函数.或者,给‘googleAuthHelperService’参数一个非空默认值.

这是因为try 将接口IGoogleAuthHelperService注入到我的控制器类中:

[Route("/auth")]
public async Task<IActionResult> AuthAsync(IGoogleAuthHelperService googleAuthHelperService)
{

        string response = await GoogleAuthHelperService.ReadHttpBodyAsync(Request.Body);
        string code = GoogleAuthHelperService.ParseGoogleResponseCode(response);
        
        //string code = Request.Body.
        await googleAuthHelperService.GetTokenAsync(code);
        if (response != null)
        {
            return View("Error");
        }
        else
        {
            return View("_Auth");
        }
}
public interface IGoogleAuthHelperService
{
    public Task<string> GetTokenAsync(string code);
}
public class GoogleAuthHelperService : IGoogleAuthHelperService
{
    private GoogleAuthSettings _settings;
    public GoogleAuthHelperService()
    {
    }
    public GoogleAuthHelperService(IGoogleAuthSettingsService googleAuthSettingsService)
    {
        if (googleAuthSettingsService.Settings != null)
        {
            _settings = googleAuthSettingsService.Settings;
        }
        else
        {
            _settings = new GoogleAuthSettings();
        }
    }
    
    public async Task<string> GetTokenAsync(string code)
    {
        HttpHelper httpHelper = new(_settings.GoogleTokenUrl); // googleauthsettings.token
        _settings.AuthorizationCode = code;
        string content = BuildGoogleTokenBody();
}
public static async Task<string> ReadHttpBodyAsync(Stream stream)
{
    using (StreamReader streamReader = new(stream))
    {
        string content = await streamReader.ReadToEndAsync();
        return content;
    }
}
}

如您所见,我将一个IGoogleAuthSettingsService类注入到我的构造函数中,该构造函数用于从appsettings.json文件中获取设置:

public interface IGoogleAuthSettingsService
{
    public GoogleAuthSettings? Settings {get; }
}
public class GoogleAuthSettingsService : IGoogleAuthSettingsService
{
    public GoogleAuthSettings? Settings { get; set;  }

}

即使当我使用IGoogleAuthSettingsService删除构造函数时,我也收到了相同的异常,并且我有点迷茫:

public interface IGoogleAuthHelperService
{
    public Task<string> GetTokenAsync(string code);
}
public class GoogleAuthHelperService : IGoogleAuthHelperService
{
    private GoogleAuthSettings _settings;
    public GoogleAuthHelperService()
    {
    }
    public GoogleAuthHelperService(IGoogleAuthSettingsService googleAuthSettingsService)
    {
        if (googleAuthSettingsService.Settings != null)
        {
            _settings = googleAuthSettingsService.Settings;
        }
        else
        {
            _settings = new GoogleAuthSettings();
        }
    }
    
    public async Task<string> GetTokenAsync(string code)
    {
        HttpHelper httpHelper = new(_settings.GoogleTokenUrl); // googleauthsettings.token
        _settings.AuthorizationCode = code;
        string content = BuildGoogleTokenBody();
}
}

下面是我将服务注册为Singleton的Program.cs:

using GmailCleaner.Models;
using GmailCleaner.Services;

var builder = WebApplication.CreateBuilder(args);

// Add services to the container.
builder.Services.AddRazorPages();

IGoogleAuthSettingsService? googleAuthService = builder.Configuration.Get<GoogleAuthSettingsService>();
builder.Services.AddSingleton<IGoogleAuthSettingsService>(googleAuthService);

GoogleAuthHelperService googleAuthHelperService = new();
builder.Services.AddSingleton<IGoogleAuthHelperService, GoogleAuthHelperService>();

var app = builder.Build();
// Configure the HTTP request pipeline.
if (!app.Environment.IsDevelopment())
{
    app.UseExceptionHandler("/Error");
    // The default HSTS value is 30 days. You may want to change this for production scenarios, see https://aka.ms/aspnetcore-hsts.
    app.UseHsts();
}

app.UseHttpsRedirection();
app.UseStaticFiles();

app.UseRouting();

app.UseAuthorization();

app.MapRazorPages();
app.MapControllers();

app.Run();

我也在我的Program.cs中try 了这样的注射:

GoogleAuthHelperService googleAuthHelperService = new();
builder.Services.AddSingleton<IGoogleAuthHelperService>(googleAuthHelperService);

有谁知道如何修复我正在注射的类吗?

推荐答案

您不能只在控制器的操作方法中使用依赖项注入.这将是一个安全风险.您有两种可能的解决方案:


1Inject the dependency in the constructor of the controller,并在控制器类的私有字段中记住它,以备将来使用.

public class YourController : Controller
{
    private readonly IGoogleAuthHelperService _googleAuthHelperService;

    public YourController(IGoogleAuthHelperService googleAuthHelperService)
    {
        _googleAuthHelperService = googleAuthHelperService;
    }

    [Route("/auth")]
    public async Task<IActionResult> AuthAsync()
    {
        // Use this._googleAuthHelperService here
    }

2在操作方法声明中的参数上使用100 attribute.

[Route("/auth")]
public async Task<IActionResult> AuthAsync
    ([FromServices] IGoogleAuthHelperService googleAuthHelperService)
{

有关更多详细信息,请参见Dependency injection into controllers in ASP.NET Core.

Csharp相关问答推荐

EF Core Fluent API中定义的多对多关系

C#类主构造函数中的调试参数

如何使用while循环实现异常处理

如何使用新的Microsoft.IdentityModel.JsonWebToken创建JwtSecurityToken?

如何使用NumberFormatInfo

共享暂存/生产环境中Azure事件中心的建议配置

异步任务导致内存泄漏

Savagger使用Fastendpoint更改用户界面参数

如何管理Azure认证客户端响应和证书 fingerprint

有没有更好的方法来在CosmosDB上插入非id?

在C#中,是否有与变量DISARD对应的C++类似功能?

为什么Azure函数(独立工作进程)索引失败?使用Azure App配置的CosmosDbTrigger绑定失败,未解析为值

数据库操作预计影响1行,但实际影响0行; after _dbContext.SaveChanges();

如何使用.NET 8.0中新的CompositeFormat类?

如何在.NET MAUI上在iOS和Mac之间共享代码?(no条件编译和无代码重复)

无效的Zip文件-Zip存档

SqlException:无法打开数据库.升级到Dotnet 8后-数据库兼容性版本-非EFCore兼容性级别

为什么INTEGER在通过反射调用时对空对象返回TRUE,而在INTEGER上调用时返回FALSE?

如何在flutter dart中使用publicKey.xml文件进行rsa加密,我遇到了问题Exception:Could not parse BigInt

需要帮助才能在图片框中显示C#(WinForm)中纯资源DLL中的图像