【发布时间】:2010-05-27 16:24:28
【问题描述】:
在具有多个支持它的数据库的分布式应用程序中,我们正在寻找更好的方法来处理数据库连接的创建。例如,假设您的系统后面有三个数据库:
- 业务数据(订单、产品、 类别等)
- 元数据(关于 业务数据的结构)
- 用户数据(用户首选项,已保存 人工制品等)
数据的细节并不重要……它只是三个数据库。在整个应用程序中,您希望获得与这三个的连接并返回一个 IDbConnection 实现。用于用户数据的实现可能与用于业务数据的实现略有不同。等等。每个连接字符串都在一个配置文件中。
所以我们研究了几种方法,包括:
具有多种方法的工厂
class ConnectionFactory {
public static IDbConnection CreateBusinessDataConnection()
{
//
}
public static IDbConnection CreateMetadataConnection()
{
//
}
public static IDbConnection CreateUserDataConnection()
{
//
}
}
... 不过,在这个例子中,我们也可以返回一个特定的实现而不是 IDbConnection 引用。缺点是我们无法在不更改消费者代码的情况下更改所使用的连接类型。
单一方法的工厂
在这种情况下,我们使用单个方法并传入一些值(可能是枚举)来指示我们想要的连接类型:
enum DbConnectionType { BusinessData, Metadata, UserData }
class ConnectionFactory {
public static IDbConnection CreateDataConnection(DbConnectionType connType)
{
// look at connType and probably use a switch statement to create
// the connection for that type.
}
}
这些都有优点和缺点...此外,我们最近开始在项目中使用 Microsoft 的 Unity IoC 容器。看起来这在这里可能很有价值,但它还处于我们理解的早期阶段。从表面上看,它似乎对我们没有帮助,因为我们没有注册具体类型。
container.Register(IDbConnection, [ which of the three implementations ? ]);
相反,它更像是我们在说“当我请求一个 IDbContainer 并且我还为你提供了这个枚举值时,请返回这个 IdbConnection 的实现。” 我们还没有找到一个在 Unity 中执行此操作的方法(但同样,它对我们来说仍然是新的,我们正在研究示例)。
想法?
【问题讨论】:
-
如果客户需要知道要建立哪种类型的连接,为什么要对他隐瞒呢?数据库的使用是否相同,即非常相似的模式?
-
对于这个特定的示例,理想情况下客户端不知道正在使用哪种类型的连接实现。我们正在使用一个开源数据库,其中有多个具有不同优点/缺点的提供商。因此,对于某些连接,我们可能会选择速度较慢但功能更多的提供商……其他人会使用速度最快的提供商。问题更多地在于采用的一般设计方法 - 给定一个通用接口,如何根据某些标志/条件/指标来决定使用哪个实现。枚举、switch 语句、某种类型的 DI 或 IoC 方法等。谢谢。
标签: c# design-patterns oop interface unity-container