2011-01-27 5 views
13

JSON과의 직렬화/역 직렬화에 jackson 라이브러리를 사용하고 있습니다. 나는이 JSON이 가능한 한 가장 작은 크기를 가질 필요가 있기 때문에 ALLOW_UNQUOTED_FIELD_NAMES 기능을 사용하여 모든 따옴표를 제거했습니다. 따옴표를 지우는 것이 표준 json이 아니라는 것을 알고 있지만 json을 작게 만드는 것은 프로젝트의 어려운 요구 사항입니다. 생성 된 JSON 작동하지만, 나는 예외 받고있어 JSON 값을 읽으려고 한 경우 :jackon의 ALLOW_UNQUOTED_FIELD_NAMES JSON 라이브러리

org.codehaus.jackson.JsonParseException : 예기치 않은 문자 ('9'(코드 57)) : 은 문자 (따옴표 붙지 않는 이름) 또는 큰 따옴표 (인용)로 시작하여 필드 이름을 시작할 것으로 예상됩니다. [출처 : [email protected]; 라인 1, 컬럼 : 3]

I이 JSON 읽을 때 상기 예외가 발생

: I는 읽어

{90110a2e-febd-470f-afa4-cf7e890d31b9:0,eec652ad-a4d9-4eb1-8d24-7c1a0c29449f:1} 

방법은 :

Map<String, Object> valuesMap = oM.readValue(json, new TypeReference<Map<String, Object>>() {}); 

대상물 값을 읽고 쓰는 데 사용하는 매퍼는 다음과 같습니다.

private static final ObjectMapper om = new ObjectMapper(); 
static { 
    om.configure(JsonGenerator.Feature.QUOTE_FIELD_NAMES, false); 
    om.configure(JsonParser.Feature.ALLOW_UNQUOTED_FIELD_NAMES, true); 
    om.configure(SerializationConfig.Feature.WRITE_DATES_AS_TIMESTAMPS, true); 
    om.configure(DeserializationConfig.Feature.FAIL_ON_UNKNOWN_PROPERTIES, false); 
    om.getSerializationConfig().setSerializationInclusion(JsonSerialize.Inclusion.NON_NULL); 
} 

나는 발신자와 수신자 프로젝트 모두에서 Jackson의 1.6.3 버전을 사용하고 있습니다. 이 기능에 필요한 버전은 1.2+입니다. 그래서이 버전을 사용하지 않고 아마도 리시버가 Spring 어플리케이션이고 libs 폴더에 설치된 라이브러리가 1.6.3인지 확인했습니다.

내가 뭘 잘못하고 있니? 지도와 함께이 기능을 사용할 수없는 경우 일 수 있습니다.

다른 질문이 있습니다. 지금까지는 키가 uuid 값이고 값이 숫자 인지도를 보내고 있습니다. ALLOW_UNQUOTED_FIELD_NAMES 기능이있는 특수 문자로 값을 보내면 문제가 생길 수 있습니까? 잭슨이이 캐릭터를 피할 것입니까?

감사합니다.

답변

5

어떤 경우에는 QUOTE_FIELD_NAMES으로 Jackson과 같아서 ALLOW_UNQUOTED_FIELD_NAMES을 켠 채로도 자체를 읽을 수없는 출력을 생성합니다. 비표준 입력 구문 분석을 위해 사용자 정의 JsonParser을 구현해야 할 것입니다.

비표준 JSON을 생성하고있어 클라이언트가 올바르게 처리하지 못한다는 것이 문제입니다. 그러나 응용 프로그램 외부에 노출시키지 않고 크기에 대해 신경 쓰지 않으면 Jackson의 Smile과 같이 바이너리 형식을 구문 분석/생성 할 수 있습니다. http://www.cowtowncoder.com/blog/archives/2010/09/entry_418.html (2.4)을 참조하십시오.

+0

스마일에 대한 좋은 점 - 특히 컴팩트 할 수 있습니다. 문자열 값 뒷쪽 참조를 사용할 때 (열거 된 값과 같은 반복 된 문자열 값이 많은 경우) – StaxMan

2

나는이 문제가 Javascript sintax와 관련이 있으며 Jackson이나 JSON과 관련이 없다고 생각한다.

자바 스크립트에서 이름은 선택적으로 하나 이상의 문자, 숫자 또는 밑줄이 뒤에 오는 문자이므로 90110a2e-febd-470f-afa4-cf7e890d31b9는 유효한 자바 스크립트 이름이 아닙니다.

이름이 유효한 JavaScript 이름이고 예약어가 아닌 경우 속성 이름 주위의 따옴표는 선택 사항입니다. 따옴표는 "이름"주위에 필요하지만 first_name 주위에서는 선택 사항입니다.

BTW, JSON 크기가 너무 우려되는 이유는 무엇입니까?

+0

감사합니다. 그러나 그것에 대해 생각해 봤지만 변수가 합법적인지 여부는 확실하지 않았습니다. json이 자바 스크립트 (Java 클라이언트에서 JEE 응용 프로그램으로 전송 됨)에 사용되지는 않지만 여러분이 말하는 것은 옳을 수도 있습니다. gzip에 관해서는, 나는 이미 json을 압축해서 보내고 있지만 어쨌든 아이디어에 감사드립니다. – Javi

6

좋아, Pingw33n의 대답은 거의 정확하다고 생각합니다. 그래서 : 예, 당신은 그 기능을 사용할 수 있습니다; 따옴표가없는 이름이 어떻게 작동해야하는지에 대한 사양이 없기 때문에 (오히려 JSON은 이름에 대해 모든 문자를 허용합니다!) 오히려 경험적입니다. 또는 어떤 탈출 메커니즘이 사용된다면 누구에게 서면으로 받아 들여지거나 받아 들여야하는지에 대해 짐작할 수 있습니다.

이 경우에는 문제를 일으키는 '-'문자 일 가능성이 큽니다. 잭슨이 사용하는 근사치 인 Javascript 이름의 합법적 인 부분이 아닙니다.

한 가지 가능한 해결책은 Jackson이 속성 이름에서 이러한 문자를 이스케이프 처리하는 것입니다 (현재 어떻게 수행되는지 기억하지 못합니다. 이름 문자가 인용 된 경우). 간단한 테스트 케이스를 파악할 수 있다면, JIRA의 요청을 Jackson Jira에 작성하여 이스케이프 처리를 추가 할 수 있습니다 (그리고 파서가 일반적인 백 슬래시 버전을 이스케이프 해제 할 수 있음).

+1

오. 사실 자바 스크립트 식별자는 숫자로 시작할 수 없기 때문에 문제가 발생합니다. ALLOW_UNQUOTED_FIELD_NAMES 모드의 경우에도이를 완화 할 수 있습니다. 이를 위해 Jira 기능 요청이 도움이 될 것입니다. – StaxMan

관련 문제