0

글쎄, 내 응용 프로그램 구조에 갇혀있는 것처럼 보입니다. 다음은 내가 원하는 작업입니다.종속성 주입이 포함 된 Entity Framework ObjectContext

  • UI 레이어 : ASP.NET webforms 웹 사이트.
  • BLL : DAL에서 리포지토리를 호출하는 비즈니스 논리 계층입니다.
  • DAL : 각 엔티티에 대한 CRUD 작업을 추상화하는 리포지토리 클래스가있는 .EDMX 파일 (Entity Model) 및 ObjectContext.
  • 개체 : POCO 개체. 지속성을 무시합니다. Microsoft의 ADO.Net POCO Entity Generator에서 생성됩니다.

내 저장소에서 성능/스레드 [un] 안전 문제를 방지하기 위해 HttpContext 당 obejctcontext를 만들고 싶습니다. 문제는 내가 (저장소가있는) 내 DAL에있는 HttpContext에 액세스하지 않을 것입니다

public MyDBEntities ctx 
{ 
    get 
    { 
     string ocKey = "ctx_" + HttpContext.Current.GetHashCode().ToString("x"); 
     if (!HttpContext.Current.Items.Contains(ocKey)) 
      HttpContext.Current.Items.Add(ocKey, new MyDBEntities()); 
     return HttpContext.Current.Items[ocKey] as MyDBEntities ; 
    } 
} 

: 이상적으로는 뭔가를 할 것이다. 하지만 어떻게 든 DAL에 HttpContext 전달해야합니다. 내 질문에 대한 대답을 기반으로 here, 나는 IoC 패턴을 사용해야합니다. 이상적으로 다층 아키텍처에서 this과 같은 것을 얻고 싶습니다.

나는 Autofac을 체크 아웃했으며 매우 유망한 것으로 보입니다. 그러나 나는 다층 아키텍처에서 어떻게이 (HttpContext 당 하나의 ObjectContext가 인스턴스화되는지 확인하기 위해 Httpcontext 전달)을 수행 할 수 있는지 잘 모르겠습니다. 아무도 이걸 달성하는 방법에 대한 몇 가지 실례를 내게 줄 수 있습니까? DAL에서 직접 HttpContext에 액세스하지 않고 DAL에서 HttpContext를 인식하는 방법은 무엇입니까? 다층 솔루션을 설계 할 때 약간의 손실이있는 것 같습니다.

답변

3

WebForms과 함께 IoC 컨테이너를 사용 해 본 적이 없으므로이 기능을 일부 개선 된 수준으로 개선해야합니다.

당신 싱글 톤 등 일부 IOC의 공급자를 만드는 시도 할 수 있습니다 :

public class IoCProvider 
{ 
    private static IoCProvider _instance = new IoCProvider(); 

    private IWindsorContainer _container; 

    public IWindsorContainer 
    { 
    get 
    { 
     return _container; 
    } 
    } 

    public static IoCProvider GetInstance() 
    { 
    return _instance; 
    } 

    private IoCProvider() 
    { 
    _container = new WindsorContainer(new XmlInterpreter(new ConfigResource("castle"))); 
    } 
} 

귀하의 web.config 같은 섹션을 포함해야합니다 (구성은 당신의 previous post에 근거) : 이러한 인터페이스의

<configuration> 
    <configSections>  
    <section name="castle" type="Castle.Windsor.Configuration.AppDomain.CastleSectionHandler, Castle.Windsor" /> 
    </configSections> 

    <castle> 
    <components> 
     <component id="DalLayer" 
       service="MyDal.IDalLayer, MyDal" 
       type="MyDal.MyDalLayer, MyDal" 
       lifestyle="PerWebRequest"> 
     <!-- 
      Here we define that lifestyle of DalLayer is PerWebRequest so each 
      time the container resolves IDalLayer interface in the same Web request 
      processing, it returns same instance of DalLayer class 
      --> 
     <parameters> 
      <connectionString>...</connectionString> 
     </parameters> 
     </component> 
     <component id="BusinessLayer" 
       service="MyBll.IBusinessLayer, MyBll" 
       type="MyBll.BusinessLayer, MyBll" /> 
     <!-- 
      Just example where BusinessLayer receives IDalLayer as 
      constructor's parameter. 
     --> 
    </components> 
    </castle> 

    <system.Web> 
    ... 
    </system.Web> 
</configuration> 

구현 수업은 다음과 같이 나타납니다.

public IDalLayer 
{ 
    IRepository<T> GetRepository<T>(); // Simplified solution with generic repository 
    Commint(); // Unit of work 
} 

// DalLayer holds Object context. Bacause of PerWebRequest lifestyle you can 
// resolve this class several time during request processing and you will still 
// get same instance = single ObjectContext. 
public class DalLayer : IDalLayer, IDisposable 
{ 
    private ObjectContext _context; // use context when creating repositories 

    public DalLayer(string connectionString) { ... } 

    ... 
} 

public interface IBusinessLayer 
{ 
    // Each service implementation will receive necessary 
    // repositories from constructor. 
    // BusinessLayer will pass them when creating service 
    // instance 

    // Some business service exposing methods for UI layer 
    ISomeService SomeService { get; } 
} 

public class BusinessLayer : IBusinessLayer 
{ 
    private IDalLayer _dalLayer; 

    public BusinessLayer(IDalLayer dalLayer) { ... } 

    ... 
} 

당신이 당신의 페이지에 대한 기본 클래스를 정의하고 비즈니스 계층을 노출 할 수 있습니다보다 (당신이 해결 될 수있는 다른 클래스와 동일한 기능을 수행 할 수 있습니다) :

public abstract class MyBaseForm : Page 
{ 
    private IBusinessLayer _businessLayer = null; 
    protected IBusinessLayer BusinessLayer 
    { 
    get 
    { 
     if (_businessLayer == null) 
     { 
     _businessLayer = IoCProvider.GetInstance().Container.Resolve<IBusinessLayer>(); 
     } 

     return _businessLayer;   
    } 

    ... 
} 

복잡한 솔루션을 직접 페이지를 해결하기 위해 사용자 정의 PageHandlerFactory를 사용하여 포함 whould 및 의존성을 주입하십시오. 그러한 솔루션 체크 Spring.NET 프레임 워크 (IoC 컨테이너가있는 다른 API)를 사용하려는 경우.

+0

Ladislav. 만약 내가 할 수 있다면, 나는 그것을 +10했습니다! – Kamyar