2014-03-07 3 views
0

REST 서비스 용 리소스 확장 기능을 빌드하려고합니다. 다음과 같은 패턴으로 리소스를 확장 할 수 있습니다.REST 서비스 용 리소스 확장 구문 분석

 

    fields=field1,field2(sf1,sf2),field3[Format],field4(sf1,sf2,sf3) 

이걸 분석하는 가장 좋은 방법은 무엇입니까? 파싱은 모든 들어오는 요청에 대해 발생해야하므로 더 나은 성능을 가져야합니다.

정규식을 정의 할 수 있는지 확인하려고합니다. 어떤 패턴을위한 정규식이 될 수 있을까요?

편집 (10 월 2014) : 문자열은 메타 데이터 (자바 필드 이름)이 포함되어 있으며

field1(sf1,sf2(sf21,sf22)),field2[Format],field3[Format],field4(sf1,sf2,sf3) 

내가 정규식을 사용하거나 수동으로 구문 분석해야 같은 멀티 레벨도 될 수 있는가?

답변

0

각 필드의 데이터 값을 모른 채 특정 RegEx를 알아내는 것은 매우 어려울 수 있습니다.

왜 POST 또는 PUT을 사용하고 데이터 본문에 데이터 값을 넣지 않습니까? 그렇게하면 JSON을 사용하여 데이터를 구성 할 수 있습니다. (OK ... XML 또는 YAML도 작동하지만 JSON을 좋아한다).

+0

기본적으로 이것은 우리가 팔로우하는/서비스중인 서비스 모델입니다. 이런 종류의 패턴은 ACCEPT 헤더에 올 것이며 우리는 그것을 분석 할 것입니다. 이러한 이름은 Java 필드 이름이므로 Java에서 필드 이름 지정에 사용할 수있는 문자를 여기에 적용 할 수 있다고 가정 할 수 있습니다. – Niranjan

+0

제 경험상, 헤더 정보를 분석해야하는 경우 특히 헤더의 거래 데이터가 좋지 않습니다. 그러나 반드시 그렇게해야한다면 표준 __? __ 표시를 사용하여 쿼리 세그먼트/필드를 구분하십시오. 자신이 제공 할 수있는 데이터로 자신을 제한하면 누군가가 (실수로 또는 다른 방법으로) 쉼표, 괄호 또는 대괄호 문자를 전달하면 쿼리가 매우 쉽게 중단됩니다. – epluribusunix

+0

안녕하세요, 저는 제대로 설명하지 못하고 있다고 생각합니다. 여기에는 어떤 데이터도 포함되지 않습니다.이 필드는 필드 이름과 같은 메타 데이터입니다. 또한 메타 데이터 만 포함됩니다. – Niranjan

1

정규식은 중첩/균형 잡힌 구문을 지원하지 않습니다. 예를 들어 수학 문을 파싱하고 모든 여는 괄호에 적절하게 균형 잡힌 닫는 괄호가 있는지 확인하거나 XML 또는 HTML을 파싱하여 모든 요소가 제대로 닫히도록하려면보다 풍부한 표현법이 필요합니다. (학문적 인 설명을 위해서는 Chomsky's Hierarchy을 참조하십시오.)

중첩 된 구문으로 언어를 구문 분석하려면 '푸시 다운 오토 마톤'과 동일한 기능이 필요합니다. PDA), 두려워하지 않습니다.이 모든 멋진 용어는 실제로 구현하기가 쉽지 않습니다. 재귀 또는 루핑을 사용하거나 각 반복 내에서 정규 표현식을 사용하여 문제를 해결하거나 자신의 파싱 메서드를 간단하게 작성할 수 있습니다.

는 최근 우리의 나머지 API에 동일한 기능을 구현, 내 구문은 약간 다릅니다 동안, 당신이 도움이 코드를 찾을 수 있습니다 생각 : 당신이에서 추측 하듯이, 우리의 경우

/** 
* Given a single packed string that defines a recursive set of fields, 
* this will parse and return a Map of terms from the root level where the 
* term is mapped to the packed string defining the sub-fields within that key. 
* 
* Assume the primary/root result is a Movie... 
*    --(raw==null) get all movie First Order (FO) attributes 
* stars  --get all movie FO, and expand stars relation 
* title  --get movies FO id and title 
* title,stars --get movies FO id and title, and expand stars relation 
* 
* stars{}  --get all movie FO, and expand stars relation (same as stars) 
* stars{name} --get all movie FO, and expand stars relation getting star FO id and name 
* stars{contractStudio} --get all movie FO, expand stars relation getting all star FO and expand stars contract studio 
* stars{name,contractStudio} --get all movie FO, and expand stars relation getting star FO id and name and expand stars contract studio 
* title,stars{name,contractStudio{name,founded}} --get movies FO id and title, and expand stars relation getting star FO id and name and expand stars contract studio with the studio FO name and founded date 
*/ 
private Map<String, String> parseRequestParameter(String raw) { 
    if (raw == null || raw.isEmpty()) return Collections.emptyMap(); 
    Map<String, String> results = new HashMap<>(); 
    int i = 0; 
    int j = 0; 
    while (j < raw.length()) { 
     char c = raw.charAt(j); 
     //move j to end of attr name 
     while (c != '{' && c != ',' && ++j < raw.length()) {c = raw.charAt(j);} 
     String attr = raw.substring(i, i = j).trim(); 
     if (!attr.isEmpty()) { 
      //capture the optional sub-expansion 
      if (c == '{') { 
       i++; //move i past the opening '{' 
       int pDepth = 1; 
       while (pDepth > 0 && ++j < raw.length()) { //pDepth is depth of nested { } 
        pDepth += (c = raw.charAt(j)) == '{' ? 1 : (c == '}' ? -1 : 0); 
       } 
       results.put(attr, raw.substring(i, j).trim()); 
       if (++j < raw.length()) c = raw.charAt(i = j); //move i and c past the closing '}' 
      } 
      else { 
       results.put(attr, null); 
      } 
     } 
     //skip any unexpected suffix trash... only ',' marks next term. 
     while ((i = ++j) < raw.length() && c != ',') {c = raw.charAt(j);} 
    } 
    return results; 
} 

을 javadoc, 확장 문자열이 지정되지 않은 경우 결과의 모든 'first order'(FO) 속성을 반환합니다. 특정 속성의 이름이 지정되면 확장 용어 (확장 할 수있는 관계 속성의 이름을 지정하는 경우) 또는 용어를 좁히는 경우 (FO 속성의 이름을 지정하는 경우). 축소 용어가 지정된 경우 렌더링 된 결과에는 다음과 같은 내용이 포함됩니다. 요청한 용어 만 또한 요청 된 용어에 관계없이 항상 ID를 반환합니다.

위의 메서드는 확장 사양을 포함하는 원시 값만 구문 분석합니다. 키가 확장 스펙의 최상위 레벨에있는 단일 용어 인 Map을 생성합니다. 값은 확장 될 때 해당 용어에 적용해야 할 확장 스펙 (압축 된 상태로 남음)입니다. 이것은 회귀가 일어나는 곳입니다. 분명히이 방법보다 높은 수준에서 발생합니다. 여기에서 얻을 수 있다고 가정합니다.

이 방법은 상당히 강력합니다. 원시 값에는 불균형 중괄호와 쓰레기 문자가 포함될 수 있다고 가정합니다. 이것들이 발생하면 그것들을 무시하고 원시 값에서 가능한 한 많이 회수합니다. 그것은 '실패 마지막'접근 방식입니다.

관련 문제