简体   繁体   English

如何为属性分配默认值

[英]How to assign default value to a property

CustomerService is a webservice and it is getting called successfully but I am unable to access SelectCommand in the Any method. CustomerService是一个Web服务,正在成功调用,但是我无法在Any方法中访问SelectCommand。 I think I am missing something here, could anyone suggest. 我想我在这里想念什么,有人可以建议。

public class CustomerService : Service
{
  private readonly IDbConnection _dbConnection; // injected successfully
  public ServiceCommand SelectCommand {get;set;}

  public CustomerService(IDBConnection dbConnection)
  {        
         _dbConnection = dbConnection;            
  }

  public Customer Any(CustomerRequest request)
  {
       //_dbconnection is available           

       //but selectcommand is null here   

       //db operations     

  }
}


[Route("/customers")]
public class CustomerRequest
{
    public string name { get; set; }
}

public class ServiceCommand
{
    public string SQL { get; set; }        
    public CommandType CommandType { get; set; }

    public ServiceCommand()
    {
        CommandType = CommandType.Text;
    }
}

I've initialized the connection by inheriting AppHostBase 我已经通过继承AppHostBase初始化了连接

  public override void Configure(Container container) {
        container.Register<IDbConnectionFactory>(
          c => new OrmLiteConnectionFactory(ConfigurationManager.ConnectionStrings["default"].ConnectionString,
                                            SqlServerDialect.Provider));

        container.Register<IDbConnection>(c => c.Resolve<IDbConnectionFactory>().OpenDbConnection()).ReusedWithin(ReuseScope.Request);
      }

When I tried to write unit test by setting SelectCommand explicitly, it works. 当我尝试通过显式设置SelectCommand编写单元测试时,它可以工作。 But I am unable to test how it works by not setting the value, I assumed it takes the default value set in the constructor. 但是我无法通过不设置值来测试它的工作方式,我假设它采用了构造函数中设置的默认值。

 var service = new CustomerService(InMemoryTestDatabase.OpenDbConnection());
 service.SelectCommand = new ServiceCommand() { SQL = "SELECT * FROM customers" };

Edit 编辑

IDbConnection in the constructor is working fine but my problem is with SelectCommand which is a public property here. 构造函数中的IDbConnection运行正常,但是我的问题是SelectCommand,这是这里的公共属性。 My intention is, if the webservice is called normally I'd hit the actual database by setting query like below in the constructor. 我的意图是,如果正常调用Web服务,则可以通过在构造函数中设置以下查询来访问实际数据库。

SelectCommand = new ServiceCommand() {Text = "sp_getcustomers"};

But when I test it, I would set it to sqllite database and change my query to table "select * from customers" since sqllite doesn't support sp's. 但是,当我对其进行测试时,我将其设置为sqllite数据库,并将查询更改为表“ select * from users”,因为sqllite不支持sp。 As mentioned unit tests are working fine, but the service is not able to initialize the public properties. 如前所述,单元测试可以正常工作,但是该服务无法初始化公共属性。

If I initialize a private readonly property same as _dbConnection like below, it works fine but I would like to inject command for the service explicitly. 如果我初始化一个与_dbConnection相同的私有只读属性,如下所示,它可以正常工作,但是我想显式注入服务命令。

private readonly IDbConnection _dbConnection;
private readonly ServiceCommand _selectCommand;
public CustomerService(IDBConnection dbConnection)
{
   __dbConnection = dbConnection;
   _selectCommand = new ServiceCommand(){Text = "sp_getCustomers"};
}

Be sure to include all relevant info and context about your question as this would be impossible to infer without out-of-hand knowledge on how you're using it. 请确保包括有关您问题的所有相关信息和上下文,因为如果没有关于如何使用的过时知识就无法推断出这一点。 Eg what does your IOC look like? 例如,您的IOC是什么样的?

You're asking for an IDbConnection in your constructor: 您在构造函数中要求一个IDbConnection

public CustomerService(IDBConnection dbConnection)
{
     SelectCommand = new ServiceCommand();
}

But it's very likely you're only registering an IDbConnectionFactory , so there doesn't exist any registered dependency with IDbConnection . 但它很可能你只是注册一个IDbConnectionFactory ,所以不存在与任何注册依赖IDbConnection

If you inheriting from Service class you've already got the IDbConnectionFactory injected and access to the IDbConnection with the base.Db property : 如果从Service类继承,则已经注入了IDbConnectionFactory并可以使用base.Db属性访问IDbConnection

private IDbConnection db;
public virtual IDbConnection Db
{
    get { return db ?? (db = TryResolve<IDbConnectionFactory>().Open()); }
}

All public properties get injected by the IOC 所有公共财产均由国际奥委会注入

The reason why SelectCommand property is null is because it's a public property. SelectCommand属性为null的原因是因为它是一个公共属性。 All of your Services public properties are attempted to be resolved by your Registered dependencies and because you don't have any registered dependencies of type ServiceCommand it is overrided with null. 尝试通过您的已注册依赖项解析所有服务的公共属性,并且由于您没有任何ServiceCommand类型的已注册依赖项,因此将其替换为null。 If this was defined in your constructor instead it would've thrown a run-time exception, because it's just a property it's initialized to null. 如果在构造函数中定义了它,则将抛出运行时异常,因为它只是一个属性,已初始化为null。

If you change the visibility of SelectCommand to protected, private, internal or static it wont be attempted to be injected by the IOC. 如果将SelectCommand的可见性更改为protected,private,internal或static,则IOC将不会尝试注入它。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM