避免全局状态

时间:2015-11-25 10:38:37

标签: c# entity-framework architecture software-design

想象一下一些SOA。我们有一些不同的服务,其中OperationContext由一些SecureOperationContext扩展,以确保满足某些安全要求。

此外,假设有时我们可能需要在其他地方的SecureOperationContext中知道某个属性,在这个SecureOperationContext中存在并且不会成为这个属性。例如,用于某种日志记录目的的用户名。

目前我们正在使用看起来和闻起来很脏的东西。胖子在我的眼中滴下了。

现在,在一些' Common'库,有一个用ThreadStatic属性定义的类:Username。我想你可以抓住我的漂移:安全的东西设置这个静态的全局变量,并且看到我们有它可用于记录puproses。

这件事让我烦恼,但另一方面还有什么可做的?我正在考虑创建一个方法,它接受一个字符串作为参数来处理这个,但是我的所有方法仍然需要读取那个非干燥的用户名属性。 所以一方面,这样一切都是在后台处理的,但我不仅仅是为了实现这一点而不得不维持一些(全局)类。

任何提示?

我不确定如何用不那么抽象的术语来表达,但这里(伪)。

public WebService
{
    public Save(Car car)
    {
        // Some SecurityCOntext is known here, this holds top secret info, 
         //  like the username
        // and sets this into the golbal helper class UserNameManagemer 

        // car has for example a CreatedDate property (from an Interface),   
        //but I don't want handle do this propertyin every Create method can handled in some general piecei of code.       


        efcontainer.AddObjcect(car)
        e.SaveChanges()  -> 
        //Now savechanges will check the objects in the ObjectSatateManager 
        //and sets the apppriopriate property via the global thing.
    }
}

现在该做些什么来摆脱这个全局变量!将用户名传递给SaveChanges是不可取的,因为我们仍然需要为所有事情手动重新设置,这会打击。

1 个答案:

答案 0 :(得分:1)

将全局属性封装在服务中。定义该服务的接口。现在,通过具有该类型的构造函数参数,依赖于您需要数据的所有位置。

这被称为dependency injection,当你想避免像现在这样的问题时,它是一个非常重要的概念。如果您拥有大型应用程序,则Autofac等依赖注入容器可以提供帮助,但并非严格要求。

最重要的是了解依赖注入并定义明确composition root,无论您是使用DI容器还是自己动手。

  

安全性设置这个静态全局变量并且看到我们可以用它来记录puproses。

这听起来像数据是动态确定的。请注意,您仍然可以使用服务来跟踪该值。该服务还知道该值是否可用。这样,您就可以更好地管理目前的时间耦合。

编辑:您可以通过工厂创建客户端对象来进一步改进设计。该工厂可以确保该值可用,因此它将客户端对象的生命周期与值的可用性相结合。这样,您可以确保始终在可以安全访问值的上下文中执行操作。