2012-06-29 2 views
1

다음 코드는, (물론) 작동하지 않습니다봄 + 몽고 + 제네릭 + 유연성

MyClass { 
    //singleton stuff 
    private static MyClass instance; 
    private MyClass() {} 
    public static MyClass getInstance() { 
     if(instance==null) { 
      instance = new MyClass(); 
     } 
     return instance; 
    } 

    // method creating problems 
    public NonGenericSuperClassOfGenericClass create(Class<?>... classes) { 
     if(someCondition) 
      return new GenericClass<classes[0],classes[1]>; // DOES NOT COMPILE 
     else 
      return new OtherGenericClass<classes[0]>; 
    } 
} 

따라서, 실제로 것 "생성"여부를 알 수없는 반환

GenericClass<classes[0],classes[1]> 

또는 매개 변수의 서로 다른 번호를

OtherGenericClass<classes[0]> 

.

내가 을 사용하고 있는데 내가 MongoDB를를 사용하려면,하지만 미래에 내가 뭔가 다른 (예를 들어, 최대 절전 모드)로 전환해야 할 수 있기 때문에이 문제가 발생합니다.

클래스 GenericClass는 뭔가 같은 :

GenericClass<PersistetType1, Long> 

또는

PersistentType1/2가 드디어 DB에 저장해야 할 클래스가 GenericClass 프록시의 일종이다, 동안이다
GenericClass<PersistentType2, Long> 

Mongo API에 액세스합니다. 사실, 모양은 다음과 같습니다.

public MongoTemplate getTemplate(); 
    public void save(T toInsert); 
    public List<T> select(Query selectionQuery); 
    public T selectById(ID id); 
    public WriteResult update(Query selectionQuery, Update updatedAttributes); 
    public void delete(T toRemove); 
    public void delete(Query selectionQuery); 

이제 무엇입니까? 컨트롤러 (또는 엔터티, 까다로운 경우)에서 저장소를 인스턴스화하고 모든 메소드를 호출해야합니다. 이로 인해 컨트롤러는 MongoDB와 결합하게됩니다. 즉, 실제로 MongoRepository라고 불리는 GenericClass를 명시 적으로 인스턴스화해야합니다. 실제로 엄격히 Mongo에 종속됩니다 (실제로는 정확히 2 개의 "자유도"가있는 일반 사항입니다).

그래서 컨트롤러를 격리하는 추가 프록시 인 MyClass를 만들기로 결정했습니다. 이 방법으로 Controller는 MyClass의 단일 인스턴스를 가져와 적절한 저장소의 새 인스턴스를 만들 수 있습니다. 특히, "somecondition"이 true 일 때, MongoRepository를 사용하고자 함을 의미합니다 (거짓 일 때, 아마도 Hibernate 프록시를 인스턴스화 할 필요성, 즉 HibernateRepository). 그러나 MongoRepository는 일반이기 때문에 매개 변수로 전달하고자하는 인스턴스화 형식이 필요합니다.

제네릭은 컴파일 할 때 해결되므로 제게 적합하지 않습니다.

어떻게 해결할 수 있습니까?

답변

2

기본 퍼시스턴스 저장소를 애플리케이션 로직에서 분리하려면 DAO 방식을 사용합니다.

DAO의 인터페이스를 필요한 방법으로 정의하십시오. 저장, 업데이트 등. 그리고 나서 당신이 필요로하는 각 퍼시스턴스 제공자에 대한 구현을 제공합니다. 예를 들어, UserAccess는 당신이 HibernateUserAccess와 MongoUserAccess로 구현할 수있는 인터페이스 일 수 있습니다. 각 구현에서 적절한 템플릿을 삽입하십시오. Mongo 또는 Hibernate를 사용하여 지속성 작업을 완료하십시오.

로드 조작이 사용자의 인스턴스를 리턴한다는 것이 문제가 될 수 있습니다. 이는 JPA 주석이 MongoDB (누출 추상화)에 필요한 스프링 데이터 주석과 다를 수 있으므로 지속성 제공자마다 다를 필요가 있습니다.

필자는 지속성 작업의 결과를 나타내고 각 지속성 공급자에 대한 구현을 갖는 사용자 인터페이스를 작성하여이를 해결할 것입니다. JPA 또는 Mongo로드 결과로 빌드하는 공통 모델을 리턴하거나 리턴하십시오.

+0

물론 그것은 해결책이지만 각 영구 엔터티에 대해 DAO를 구현해야합니다. 많은 노력이 필요하기 때문에 그렇게하고 싶지는 않습니다. 제공된 지속성을 전환 할 확률은 상당히 낮습니다. 차라리 20/25 엔티티를 MongoDB와 결합시켜 공급자를 변경하지 말라는 사실에 도박을 걸고 싶습니다. – Manu

+0

나는 그 때 그것을 할 것입니다. 지속성 공급자 변경은 자주 발생하는 일이 아닙니다. 어쨌든 25 개의 엔티티를 업데이트하는 작업은 그리 크지 않습니다. –