2009-04-22 2 views
2

필자는 (회계 응용 프로그램과의 인터페이스 인) 오히려 특이한 데이터 소스를 가지고 있습니다. 꽤 강력한 반면, 나는 그것에서 원하는 데이터를 얻기 위해 꽤 많은 농구를 뛰어 넘어야합니다. 예를 들어, 테이블의 내용을 가져 와서 반환해야하는 열을 지정하려면 .Columns 컬렉션을 반복하고 .SetVisible()을 원하는 것으로 호출해야합니다.DSL과 메서드 호출 : 장단점

현재 우리는이 문제를 감싸고 더 간단한 방법으로 항목을 지정할 수있는 방법을 가지고 있지만 그 기능에 대한 매개 변수 목록은 빠르게 증가하고 있으며 대부분은 몇 가지를 지정해야합니다 우리가 그것을 부를 때. 즉, 유연하지 못한 솔루션입니다. 내 마음에 온

첫 번째 솔루션은 다음과 같이이었다 :

DataTable result = DataSourceWrapper.StartQuery("TableName") 
    .SetVisibleColumns("Col1", "Col2", "Col3") 
    .SetCriteria("CriteriaName", "Param1Name", CriteriaParam1, "Param2Name", CriteriaParam2) 
    .SetFilter("Col4 = ? AND Col5 = ?", FilterParam1, FilterParam2) 
    .SetReportParams("Param1Name", ReportParam1, "Param2Name", ReportParam2) 
    .Execute(); 

기준, 필터 및 ReportParams 응용 프로그램에 고유 한 몇 가지이며, 나는 여기에 대해 논의하지 않을 것이다. 그러나 일반적인 생각은 이것과 같습니다. 특정 메서드를 호출하여 지정할 매개 변수를 선택하고 IntelliSense 지원을 조금 더 가질 수 있다는 점을 제외하면 실제로 메서드를 호출하는 것과 비슷합니다. 또한 메소드 호출 순서로 재생할 수도 있습니다.

SetFilter()에는 구문 분석 할식이 있습니다. 이것은 DataSource가 어렵게 만드는 또 다른 것입니다. 꽤 멋진 표현식을 처리 할 수 ​​있지만 특수 객체 트리로 전달해야합니다.이 객체는 다시 작성하는 데 시간이 오래 걸립니다. previous question에서 그러한 표현을 구문 분석하는 데 도움을 요청했습니다. 현재 래퍼 메서드는 간단한 식을 구문 분석 할 수있는 자작 식 구문 분석기를 가지고 있지만 더 완벽하게 지원할 생각입니다.

이 질문에서 Irony 프로젝트가 제안되었습니다. 그것을 확인한 후에 나는 그것이 실제로이 필요에 적합하다고 결정했다. 그러나 잠시 후 나보다 더 강력 해졌습니다. 왜 내 자신의 쿼리 언어를이 작업에 맞게 만들지 않겠습니까? 위의 내용은 다음과 같습니다.

DataTable result = DataSourceWrapper.Query(@" 
    SELECT Col1, Col2, Col3 
    FROM TableName 
    WITH CRITERIA CriteriaName(Param1Name={0}, Param2Name={1}) 
    WITH REPORTPARAMS (Param1Name={2}, Param2Name={3} 
    WHERE Col4 = {4} AND Col5 = {5}", 
    CriteriaParam1, CriteriaParam2, 
    ReportParam1, ReportParam2, 
    FilterParam1, FilterParam2 
); 

하지만 ... 과장이 아닐까요? 두 가지 접근 방식의 장단점은 무엇입니까? 내가 볼 것은 :

프로 DSL :

  • 질의보다 간결;

프로 방법 :

  • 더 IntelliSense를 지원,
  • 메소드 이름/매개 변수 이름 (및 주석)은 문서 작성을 덜 필요로합니다 (DSL은 철저히 문서화해야합니다).
  • 더 빨리 만들 수 있습니까? 나는 내 자신의 DSL을 만든 적이 없으므로 나는 얼마나 많은 일이 있는지 모른다. 아이러니 한 점은 내 어깨에서 많은 부담을 느끼는 것 같지만, 아직 얼마나 남아 있습니까?

올린 날짜 : 분명히하기 위해 두 가지 방법 모두 코더에 의해서만 사용됩니다. 외부 사용자 및 비즈니스 분석가는이를 사용하지 않습니다.

답변

2

DSL이라고 부르는 것에 조심해야합니다. Martin Fowler's Bliki post on DSL을 참조하십시오. 메서드 체이닝의 예는 내부 DSL에 매우 가깝습니다. 약간 수정과는 다음과 같습니다

말했다되고 그건
DataTable result = DataSourceWrapper.Query("TableName") 
    .With(new Columns("Col1", "Col2", "Col3")) 
    .Where(new AndCritera("CriteriaName", 
     new Criterion("Param1Name", CriteriaParam1), 
     new Criterion("Param2Name", CriteriaParam2)) 
    .Filter(
     new Filter("Col4").Equals(FilterParam1), 
     new Filter("Col5").Equals(FilterParam2)) 
    .With(
     new ReportParam("Param1Name", ReportParam1), 
     new ReportParam("Param2Name", ReportParam2)); 

, 이것은 대단히 C 번호 영역 내에서 여전히, 오직 프로그래머는 이러한 쿼리를 작성 할 수 있습니다. 프로그래머가 아닌 사람도 쿼리를 사용할 수 있도록 요구 사항을 추진하고 있다면 두 번째 예제에서 지정한대로 외부 DSL을 만드는 노력을 고려해야합니다.

+0

아니요, 이것은 우리 내부 프로그래머 만 사용할 수 있습니다. 그리고, 맞습니다. 그것이 정확하게 요점입니다. 나는 실제 DSL에 아주 가깝다. 다음 단계는 그것을 만드는 것이다. 코드의 작성을 더 쉽게하기 위해서 DSL이 그 부분에서 이긴다. (여기서 작성한 것보다 더 짧다.)하지만 나를 만들 때 얼마나 오래 걸릴지 걱정된다. 그리고 내가 모르는 다른 장애물이있을 수도 있습니다. –

+0

유일하게 소비자가 C# 프로그래머가 될 경우 완전히 외부 DSL을 만드는 데 부가 가치가 없다고 제안합니다. 프로그래머는 Visual Studio를 사용하여 내부 DSL과 쉽게 상호 작용할 수 있기 때문에 실제로 시간 낭비로 끝납니다. –

0

DSL 방식을 선택했습니다.

이유 : 1 개인적인 경험에서, 도메인 전문가에 가깝다는 DSL의 형태로 뭔가 같은 BAS, 그것은 비즈니스 생각을 가진 사람과 개발자 사이의 통신 장벽을 나누기 및 기술 사양 을 훨씬 쉽게 작성하게 2 아이러니 (Irony)와 같은 도구를 사용하면 DSL이 잘 정의되고 테스트 구동 개발을위한 좋은 후보가 될 것입니다. (DSL을 구현하는 데에는 개발자에게 약간의 초기 학습이 필요합니다. 아이러니보다 덜 우호적 인 javacc를 사용합니다. 일단 아이디어를 이해하면 쉽게 될 수 있고 DSL로 로직을 오프로드하기 때문에 코드가 매우 일반적으로된다.