DLL在EXE中调用对象的最佳实践

时间:2009-03-18 11:39:50

标签: .net vb.net

我正在使用几个需要访问应用程序LINQ DataContext的“主”对象构建DLL。 DLL将为具有不同dataContexts的几个项目提供服务,因此我需要DLL可以调用它在EXE中的对象。

最好或最优雅的方法是什么?

编辑:澄清
我正在尝试做的代码示例:

'DLL
'---
Public MustInherit Class MasterObject(Of T As Class)
   Friend db As DataContext
   Public Sub New()
      'How do I do something like this?
      db = New DataContextInTheExe()
   End Sub

   ...

   Public MustOverride Sub Save()
end class

'In the Exe
'---
Public Class Order
   Inherits MasterObject(Of Order)

   Public Overrides Sub Save()
       ...
       Me.db.SubmitChanges()
   End Sub
end class

3 个答案:

答案 0 :(得分:3)

通过将数据上下文传递给需要在DLL中使用它的类(通常通过其构造函数)来使用依赖注入。

这是C#中的一个例子:

public abstract class MasterObject<T>
{
   private DataContext _dataContext;

   public MasterObject(DataContext dataContext)
   {
      _dataContext = dataContext;
   }
}

public class Order : MasterObject<Order>
{
   public Order(DataContext dataContext) : base(dataContext)
   {
      // additional constructor logic
   }
}

答案 1 :(得分:2)

最合适的方法是让exe将数据上下文传递给dll,例如作为dll正在执行的任何方法的方法参数,或者作为任何类的构造函数参数(在dll中)需要它。如果您有不同类型的数据上下文,则类型必须是DataContext或子类。扩展方法(在DataContext上)是这样做的一种方式(但不是唯一的方法)。

或者 - 在标准的“存储库”实现中(其中dll是存储库),调用者(exe)完全有可能甚至不知道数据上下文 - 只有ICustomerRepository dll公开的接口(或其他)。


重新编辑;仅凭这一点,就无法知道要创建的数据上下文的类型。您可能需要 传递数据上下文,或者告诉它(通过泛型)数据上下文的类型;请原谅我的C#,但是:

public abstract class MasterObject<TDataContext, TEntity>
    where TDataContext : DataContext, new()
    where TEntity : class
{
    internal TDataContext db;
    public MasterObject() {
        db = new TDataContext();
    }
}

但是,我强烈怀疑依赖注入路由更简单 - 即让来电者告诉我们:

public abstract class MasterObject<TEntity>
    where TEntity : class
{
    internal DataContext db;
    public MasterObject(DataContext db) {
        this.db = db;
    }
}

答案 2 :(得分:1)

目前还不清楚你想做什么,所以我会指出你发布的一些相关答案:

关于结构图,我们的想法是你称之为:

var someMaster = StructureMap.GetInstance<SomeMasterDefinedInDll>();

Structure Map将实例化并传递SomeMasterDefinedInDll构造函数所需的任何内容。您确实需要对其进行配置,因此在请求DataContext时告诉它获取在exe中定义的上下文。现在,通常SomeMasterDefinedInDll是其他东西的依赖项,因此您甚至不需要在上面创建该代码(它是其他东西的构造函数的参数),您只能在层次结构的顶部执行此操作。检查链接,在那里解释清楚。

更新:在c#语法中,你会:

public abstract class MasterObject<T>
{
    protected MasterObject(DataContext context)
    {
    }
}
public class Order : MasterObject<Order>
{
    public Order() : base(new ExeDataContext()) {}
}

基本上,接收datacontext作为构造函数参数,并在子类中将datacontext传递给基础构造函数。

更新2:请注意,上面的代码是对您最初想要做的回复。如果你只是想这样做,那就行了(不需要其他的东西)。也就是说,我建议你研究依赖注入。在这种情况下,也会在Order构造函数中接收ExeDataContext: public Order(ExeDataContext context):base(context){}