【问题标题】:.NET 6 WebApi Error using Visual Studio 2022 Current.NET 6 WebApi 错误使用 Visual Studio 2022 当前
【发布时间】:2021-12-31 19:46:00
【问题描述】:

使用 .NET 6 和 Visual Studio 2022 Current,当我尝试在 Swagger 中测试 API 时出现错误。尝试激活时无法解析服务类型。另外,当我像 builder.Services.AddSingleton();

System.AggregateException:'某些服务无法构造(验证服务描述符时出错'ServiceType:WebApi.Utilities.IDataAcess Lifetime:Singleton ImplementationType:WebApi.Utilities.DataAcess':无法解析类型'的服务' WebApi.Utilities.DBAccess' 同时尝试激活'WebApi.Utilities.DataAcess'。)'

当我运行应用程序时,我得到了如图所示的错误。

我很确定问题出在哪里,但每当我尝试在 .Net 5 或更低版本中添加服务时,它都能正常工作。

控制器

    using Microsoft.AspNetCore.Mvc;
    using WebApi.Models;
    using WebApi.Utilities;
    
    namespace WebApi.Controllers
    {
        [ApiController]
        [Route("analysis")]
        public class analysisDataController : ControllerBase
        {
            private IDataAcess _dataAcess;
            public analysisDataController(IDataAcess dataAcess)
            {
                _dataAcess = dataAcess;
            }
    
            [HttpGet]
            public ActionResult<IEnumerable<Clients>> getAllClients()
            {
                return _dataAcess.getClients().ToList();
            }
        }
    }

型号

    using System.ComponentModel.DataAnnotations;
    
    namespace WebApi.Models
    {
        public class Clients
        {
            [Required]
            public Guid id { get; set; }
            [Required]
            public string usercode { get; set; }
            [Required]
            public int clientid { get; set; }
            [Required]
            public string clientName { get; set; }
            [Required]
            public int searchId { get; set; }
            [Required]
            public string searchName { get; set; }
        }
    }

数据访问

    using WebApi.Models;
    
    namespace WebApi.Utilities
    {
        public class DataAcess : IDataAcess
        {
            IDBAccess _dbAccess;
            public DataAcess(DBAccess dBAccess)
            {
                _dbAccess = dBAccess;
            }
    
            public List<Clients> getClient(string user)
            {
                string query = @"SELECT u.UserID AS USER, uc.clientID AS clientID, cl.Name AS clientName,search.ID AS searchID, search.Description AS searchName 
                                     FROM testdb1.user_client AS uc
                                    JOIN testdb2.client AS cl ON uc.clientID = cl.ID
                                    JOIN testdb1.user AS u ON u.ID = uc.userID
                                     JOIN testdb2.set ON set.IDClient = uc.clientID
                                    JOIN testdb2.search ON search.IDSet = set.ID
                                     WHERE u.UserID = '" + user + "'";
                if (!string.IsNullOrEmpty(user))
                {
                    var clientData = _dbAccess.RunQuery<Clients>(query);
    
                    return clientData.ToList();
                }
                else
                {
                    return null;
                }
            }
    
            public IEnumerable<Clients> getClients()
            {
                string query = @"SELECT u.UserID AS USER, uc.clientID AS clientID, cl.Name AS clientName,search.ID AS searchID, search.Description AS searchName 
                                     FROM testedb1.user_client AS uc
                                    JOIN testdb1.client AS cl ON uc.clientID = cl.ID
                                    JOIN testdb1.user AS u ON u.ID = uc.userID
                                     JOIN testdb2.set ON set.IDClient = uc.clientID
                                    JOIN testdb2.search ON search.IDSet = set.ID";
    
                var clients = _dbAccess.RunQuery<Clients>(query);
                if(clients.Count != 0)
                    return clients;
    
                return null;
            }
        }
    }


DBAccess 类

    using Dapper;
    using MySql.Data.MySqlClient;
    
    namespace WebApi.Utilities
    {
        public class DBAccess : IDBAccess
        {
            ILogger _logger;
    
            public DBAccess(ILogger logger)
            {
                _logger = logger;
            }
            public List<T> RunQuery<T>(string query)
            {
                try
                {
                    const string conStr = @"server='####';userid='Aubz';password='Test';database='testdb1.clients'";
                    using (MySqlConnection conn = new MySqlConnection(conStr))
                    {
                        return conn.Query<T>(query).ToList();
                    }
                }
                catch (Exception e)
                {
                    _logger.log(e.Message);
                    throw e;
                }
    
            }
        }
    }

记录器类

        namespace WebApi.Utilities
        {
        public class Logger : ILogger
        {
            public void log(string logData)
            {
                Console.WriteLine(logData);
            }
        }
    }

接口类 IDataAcess

    using WebApi.Models;
    
    namespace WebApi.Utilities
    {
        public interface IDataAcess
        {
            List<Clients> getClient(string user);
            IEnumerable<Clients> getClients();
        }
    }

接口 IDBAccess

    namespace WebApi.Utilities
    {
        public interface IDBAccess
        {
            List<T> RunQuery<T>(string query);
        }
    }

界面记录器

    namespace WebApi.Utilities
    {
        public interface ILogger
        {
            void log(string logData);
        }
    }

Program.cs

    using WebApi.Utilities;
    
    var builder = WebApplication.CreateBuilder(args);
    
    // Add services to the container.
    
    builder.Services.AddControllers();
    // Learn more about configuring Swagger/OpenAPI at https://aka.ms/aspnetcore/swashbuckle
    builder.Services.AddEndpointsApiExplorer();
    builder.Services.AddSwaggerGen();
    
    var app = builder.Build();
    
    // Configure the HTTP request pipeline.
    if (app.Environment.IsDevelopment())
    {
        app.UseSwagger();
        app.UseSwaggerUI();
    }
    
    app.UseHttpsRedirection();
    
    app.UseAuthorization();
    
    app.MapControllers();
    
  app.Run();

【问题讨论】:

  • 这不是 VS 2022 问题,甚至不是任何 Visual Studio 问题,您根本没有注册该服务。可能类似于builder.Services.AddSingleton&lt;IDataAcess,DataAcess&gt;()。虽然你真的应该看看如何使用依赖注入
  • 我确实添加了 builder.Services.AddSingleton();一开始就像我们在 .NET 5 中使用它一样,但我收到以下错误:System.AggregateException:'无法构造某些服务(验证服务描述符时出错'ServiceType:WebApi.Utilities.IDataAcess Lifetime:Singleton ImplementationType :WebApi.Utilities.DataAcess':尝试激活'WebApi.Utilities.DataAcess'时,无法解析类型'WebApi.Utilities.DBAccess'的服务。)'
  • 根据报错,需要注册的不是DataAcess,而是DBAccess

标签: c# .net asp.net-core asp.net-web-api dependency-injection


【解决方案1】:

问题是你没有配置Dependency injection Container

  1. 您的控制器依赖于IDataAcess,但您没有为其提供任何具体实现,请将DataAcess 添加为program.cs 中的Concert 实现
builder.Services.AddSingleton<IDataAcess,DataAcess>();
  1. DataAcess 依赖于具体的DBAccess 并将其存储为IDBAccess,这是毫无意义的,你的类应该依赖于接口而不是具体
IDBAccess _dbAccess;
public DataAcess(IDBAccess dBAccess)  //<<< change to be depend on interface IDBAccess 
{
    _dbAccess = dBAccess;
}
  1. program.cs中为IDBAccess提供具体实现
builder.Services.AddSingleton<IDBAccess ,DBAccess>();

最后,你的 program.cs 会是这个样子

using WebApi.Utilities;
    
var builder = WebApplication.CreateBuilder(args);
    
// Add services to the container.
builder.Services.AddSingleton<IDBAccess ,DBAccess>();   //<<<< adding IDBAccess
builder.Services.AddSingleton<IDataAcess,DataAcess>();  //<<<<< adding IDataAcess
    
builder.Services.AddControllers();
// Learn more about configuring Swagger/OpenAPI at https://aka.ms/aspnetcore/swashbuckle
builder.Services.AddEndpointsApiExplorer(); 
builder.Services.AddSwaggerGen();
    
var app = builder.Build();  
// Configure the HTTP request pipeline.
if (app.Environment.IsDevelopment())
{
   app.UseSwagger();
   app.UseSwaggerUI();
}  
app.UseHttpsRedirection();   
app.UseAuthorization();   
app.MapControllers();
app.Run();

【讨论】:

  • 感谢您回复我,我确实添加了 builder.Services.AddSingleton(): 但出现错误。 System.AggregateException:'无法构造某些服务(验证服务描述符时出错'ServiceType:WebApi.Utilities.IDataAcess Lifetime:Singleton ImplementationType:WebApi.Utilities.DataAccess:无法解析类型'WebApi.Utilities。尝试激活 'WebApi.Utilities.DataAcess' 时的 DBAccess'。)'
  • 此错误消息说您没有在步骤 2 中添加 IDBAccess ...请阅读答案并确保从步骤 2 ...您是否将 DataAcess 构造函数更改为IDBAccess 不是 DBAccess ?
  • 感谢您回复我。你指的是这部分吗?如果是,请您进一步详细说明。公共数据访问(DBAccess dBAccess){_dbAccess = dBAccess; }
  • 是的,我的意思是,你应该把它改成public DataAcess(IDBAccess dBAccess) { _dbAccess = dBAccess; } ,你应该使用接口IDBAccess而不是具体的DBAccess,并确保将它添加到依赖容器builder.Services.AddSingleton&lt;IDBAccess ,DBAccess&gt;();中程序.cs
  • 谢谢,我知道了,现在可以使用了。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2022-10-17
  • 1970-01-01
  • 2022-10-30
  • 2022-07-13
  • 2022-08-15
  • 2022-08-18
相关资源
最近更新 更多