דוגמאות להערות ג'קסון

1. סקירה כללית

במדריך זה, נבצע צלילה עמוקה הערות ג'קסון.

נראה כיצד להשתמש בהערות הקיימות, כיצד ליצור הערות מותאמות אישית, ולבסוף, כיצד להשבית אותן.

2. הערות סידור ג'קסון

ראשית, נסתכל על הערות הסידור.

2.1. @JsonAnyGetter

ה @JsonAnyGetter ביאור מאפשר גמישות השימוש ב- מַפָּה שדה כתכונות סטנדרטיות.

לדוגמא, ה ExtendableBean ישות יש את שֵׁם מאפיין וקבוצת תכונות הניתנות להרחבה בצורה של צמדי מפתח / ערך:

מחלקה ציבורית ExtendableBean {שם מחרוזת ציבורי; נכסי מפה פרטיים; @JsonAnyGetter מפה ציבורית getProperties () {נכסים חוזרים; }}

כאשר אנו מבצעים סדרת מופע של ישות זו, אנו מקבלים את כל ערכי המפתח ב- מַפָּה כסטנדרט, מאפיינים פשוטים:

{"name": "שעועית שלי", "attr2": "val2", "attr1": "val1"}

כך נראה סדרת היישות הזו בפועל:

@ מבחן ציבורי בטל כאשר SerializingUsingJsonAnyGetter_thenCorrect () זורק JsonProcessingException {ExtendableBean שעועית = חדש ExtendableBean ("שעועית שלי"); bean.add ("attr1", "val1"); bean.add ("attr2", "val2"); תוצאת מחרוזת = ObjectMapper חדש (). WriteValueAsString (שעועית); assertThat (תוצאה, containString ("attr1")); assertThat (תוצאה, containString ("val1")); }

אנו יכולים גם להשתמש בטיעון האופציונלי מופעלת כפי ש שֶׁקֶר להשבית @JsonAnyGetter (). במקרה זה, מַפָּה יומר כ- JSON ויופיע תחת ה- נכסים משתנה לאחר סידור.

2.2. @JsonGetter

ה @JsonGetter ביאור הוא אלטרנטיבה ל @JsonProperty ביאור, המסמן שיטה כשיטת גטר.

בדוגמה הבאה אנו מציינים את השיטה getTheName () כשיטת גטר של שֵׁם רכוש של א MyBean יֵשׁוּת:

מחלקה ציבורית MyBean {מזהה ציבורי אינטנסיבי; שם מחרוזת פרטי; @JsonGetter ("שם") מחרוזת ציבורית getTheName () {שם החזרה; }}

כך זה עובד בפועל:

@ מבחן ציבורי בטל כאשר SerializingUsingJsonGetter_thenCorrect () זורק JsonProcessingException {שעועית MyBean = MyBean חדש (1, "שעועית שלי"); תוצאת מחרוזת = ObjectMapper חדש (). WriteValueAsString (שעועית); assertThat (תוצאה, containString ("השעועית שלי")); assertThat (תוצאה, containString ("1")); }

2.3. @JsonPropertyOrder

אנחנו יכולים להשתמש ב- @JsonPropertyOrder ביאור לציין סדר המאפיינים בסידור.

בואו נקבע סדר מותאם אישית למאפיינים של a MyBean יֵשׁוּת:

@JsonPropertyOrder ({"name", "id"}) מחלקה ציבורית MyBean {id מזהה ציבורי; שם מחרוזת ציבורי; }

הנה תפוקת הסידור:

{"name": "השעועית שלי", "id": 1}

אז נוכל לעשות בדיקה פשוטה:

@ מבחן ציבורי בטל כאשר SerializingUsingJsonPropertyOrder_thenCorrect () זורק JsonProcessingException {שעועית MyBean = MyBean חדש (1, "שעועית שלי"); תוצאת מחרוזת = ObjectMapper חדש (). WriteValueAsString (שעועית); assertThat (תוצאה, containString ("השעועית שלי")); assertThat (תוצאה, containString ("1")); }

אנחנו יכולים גם להשתמש @JsonPropertyOrder (אלפבית = נכון) לסדר את המאפיינים לפי אלפבית. במקרה זה, תפוקת הסידור תהיה:

{"id": 1, "name": "השעועית שלי"}

2.4. @JsonRawValue

ה @JsonRawValue ביאור יכול להורות לג'קסון לסדר נכס בדיוק כמו שהוא.

בדוגמה הבאה אנו משתמשים @JsonRawValue להטמיע JSON מותאם אישית כערך של ישות:

מחלקה ציבורית RawBean {שם מחרוזת ציבורי; @JsonRawValue מחרוזת json ציבורית; }

התפוקה של סדרת היישות היא:

{"name": "שעועית שלי", "json": {"attr": false}}

להלן מבחן פשוט:

@ מבחן פומבי בטל כאשר SerializingUsingJsonRawValue_thenCorrect () זורק JsonProcessingException {שעועית RawBean = RawBean חדש ("השעועית שלי", "{\" attr \ ": false}"); תוצאת מחרוזת = ObjectMapper חדש (). WriteValueAsString (שעועית); assertThat (תוצאה, containString ("השעועית שלי")); assertThat (תוצאה, containString ("{\" attr \ ": false}")); }

אנו יכולים להשתמש גם בטיעון הבוליאני האופציונלי ערך המגדיר אם הערה זו פעילה או לא.

2.5. @JsonValue

@JsonValue מציין שיטה אחת בה הספרייה תשתמש לסידור המופע כולו.

לדוגמא, באנום אנו מציינים את ה- getName עם @JsonValue כך שכל ישות כזו מסודרת באמצעות שמה:

enum ציבור TypeEnumWithValue {TYPE1 (1, "סוג A"), TYPE2 (2, "Type 2"); מזהה שלם פרטי; שם מחרוזת פרטי; // קונסטרוקטורים סטנדרטיים @ JsonValue מחרוזת ציבורית getName () {שם השבה; }}

עכשיו הנה המבחן שלנו:

@ מבחן ציבורי בטל כאשר SerializingUsingJsonValue_thenCorrect () זורק JsonParseException, IOException {String enumAsString = חדש ObjectMapper () .writeValueAsString (TypeEnumWithValue.TYPE1); assertThat (enumAsString, הוא ("" סוג A "")); }

2.6. @JsonRootName

ה @JsonRootName הערה משמשת, אם העטיפה מופעלת, כדי לציין את שם עטיפת השורש לשימוש.

עיטוף פירושו שבמקום לסדר א מִשׁתַמֵשׁ למשהו כמו:

{"id": 1, "name": "John"}

זה יהיה עטוף כך:

{"משתמש": {"id": 1, "name": "John"}}

אז בואו נסתכל על דוגמא. Wאתה הולך להשתמש ב- @JsonRootName ביאור לציין את שם ישות העטיפה הפוטנציאלית הזו:

@JsonRootName (value = "user") מחלקה ציבורית UserWithRoot {id מזהה ציבורי; שם מחרוזת ציבורי; }

כברירת מחדל, שם העטיפה יהיה שם המחלקה - UserWithRoot. על ידי שימוש בהערה, אנו מנקים את המנקה מִשׁתַמֵשׁ:

@ מבחן פומבי בטל כאשר SerializingUsingJsonRootName_thenCorrect () זורק את JsonProcessingException {UserWithRoot user = משתמש חדש (1, "John"); ממפה ObjectMapper = ObjectMapper חדש (); mapper.enable (SerializationFeature.WRAP_ROOT_VALUE); תוצאת מחרוזת = mapper.writeValueAsString (משתמש); assertThat (תוצאה, containString ("ג'ון")); assertThat (תוצאה, containString ("משתמש")); }

הנה תפוקת הסידור:

{"user": {"id": 1, "name": "John"}}

מאז ג'קסון 2.4, טיעון אופציונלי חדש מרחב שמות זמין לשימוש עם פורמטים של נתונים כגון XML. אם נוסיף אותו, זה יהפוך לחלק מהשם המוסמך:

@JsonRootName (value = "user", namespace = "users") מחלקה ציבורית UserWithRootNamespace {id מזהה ציבורי; שם מחרוזת ציבורי; // ...}

אם אנחנו מסדרים את זה עם XmlMapper, התפוקה תהיה:

 ג'ון 1 

2.7. @JsonSerialize

@JsonSerialize מציין סדרטור מותאם אישית לשימוש כאשר מארשל הישות.

בואו נסתכל על דוגמה מהירה. אנחנו הולכים להשתמש @JsonSerialize לסדר את תאריך אירוע נכס עם CustomDateSerializer:

class class EventWithSerializer {שם מחרוזת ציבורי; @JsonSerialize (באמצעות = CustomDateSerializer.class) תאריך ציבורי eventDate; }

הנה הסידור הפשוט של ג'קסון המותאם אישית:

מחלקה ציבורית CustomDateSerializer מרחיב StdSerializer {פרטי סטטי SimpleDateFormat מעצב = חדש SimpleDateFormat ("dd-MM-yyyy hh: mm: ss"); Public CustomDateSerializer () {this (null); } CustomDateSerializer ציבורי (Class t) {super (t); } @Override בטל פומבי בסידור (ערך תאריך, JsonGenerator gen, SerializerProvider arg2) זורק IOException, JsonProcessingException {gen.writeString (formatter.format (value)); }}

עכשיו בואו נשתמש באלה במבחן:

@ מבחן ציבורי בטל כאשר SerializingUsingJsonSerialize_thenCorrect () זורק את JsonProcessingException, ParseException {SimpleDateFormat df = new SimpleDateFormat ("dd-MM-yyyy hh: mm: ss"); מחרוזת toParse = "20-12-2014 02:30:00"; תאריך תאריך = df.parse (toParse); EventWithSerializer event = EventWithSerializer חדש ("מסיבה", תאריך); תוצאת מחרוזת = ObjectMapper חדש (). WriteValueAsString (אירוע); assertThat (תוצאה, containString (toParse)); }

3. ביאורים על התפטרות ג'קסון

לאחר מכן בואו נחקור את הערות העריקות של ג'קסון.

3.1. @JsonCreator

אנחנו יכולים להשתמש ב- @JsonCreator ביאור כדי לכוון את הבנאי / המפעל המשמש לניתוק עריקה.

זה מאוד שימושי כשאנחנו צריכים לנתק מחדש את JSON כלשהו שאינו תואם בדיוק את ישות היעד שאנו צריכים לקבל.

בואו נסתכל על דוגמא. נניח שעלינו לבטל את ערכת ה- JSON הבאה:

{"id": 1, "theName": "השעועית שלי"}

עם זאת, אין השם בשדה היעד שלנו, יש רק א שֵׁם שדה. עכשיו אנחנו לא רוצים לשנות את היישות עצמה, אנחנו רק צריכים קצת יותר שליטה על תהליך הנטייה המאוחסן על ידי הערת הבנאי עם @JsonCreator, ושימוש ב- @JsonProperty ביאור גם:

מחלקה ציבורית BeanWithCreator {מזהה ציבורי; שם מחרוזת ציבורי; @JsonCreator הציבור BeanWithCreator (@JsonProperty ("id") מזהה int, @JsonProperty ("theName") שם מחרוזת) {this.id = id; this.name = שם; }}

בואו נראה את זה בפעולה:

@ מבחן ציבורי בטל כאשרDererializingUsingJsonCreator_thenCorrect () זורק IOException {String json = "{\" id \ ": 1, \" theName \ ": \" השעועית שלי \ "}"; שעועית BeanWithCreator = ObjectMapper חדש () .readerFor (BeanWithCreator.class) .readValue (json); assertEquals ("שעועית שלי", שעועית שם); }

3.2. @JacksonInject

@JacksonInject מציין כי נכס יקבל את ערכו מההזרקה ולא מנתוני JSON.

בדוגמה הבאה אנו משתמשים @JacksonInject להזרים את הרכוש תְעוּדַת זֶהוּת:

מחלקה ציבורית BeanWithInject {@JacksonInject מזהה מידע ציבורי; שם מחרוזת ציבורי; }

ככה זה עובד:

@ מבחן ציבורי בטל כאשרDeserializingUsingJsonInject_thenCorrect () זורק IOException {String json = "{\" name \ ": \" שעועית שלי \ "}"; InjectableValues ​​inject = new InjectableValues.Std () .addValue (int.class, 1); שעועית BeanWithInject = ObjectMapper חדש (). קורא (הזרקה). ForType (BeanWithInject.class) .readValue (json); assertEquals ("שעועית שלי", שעועית שם); assertEquals (1, bean.id); }

3.3. @JsonAnySetter

@JsonAnySetter מאפשר לנו את הגמישות בשימוש ב- מַפָּה כמאפיינים סטנדרטיים. בעת עריקת ייעול, המאפיינים של JSON יתווספו פשוט למפה.

ראשית, נשתמש @JsonAnySetter לנטרל את היישות ExtendableBean:

מחלקה ציבורית ExtendableBean {שם מחרוזת ציבורי; נכסי מפה פרטיים; @JsonAnySetter הוסף חלל ציבורי (מפתח מחרוזת, ערך מחרוזת) {property.put (מפתח, ערך); }}

זהו ה- JSON שעלינו לנתק מחדש:

{"name": "שעועית שלי", "attr2": "val2", "attr1": "val1"}

אז איך הכל מתקשר ביחד:

@ מבחן ציבורי בטל כאשרDererializingUsingJsonAnySetter_thenCorrect () זורק IOException {String json = "{\" name \ ": \" שעועית שלי \ ", \" attr2 \ ": \" val2 \ ", \" attr1 \ ": \" val1 \ "}"; ExteanableBean שעועית = ObjectMapper חדש () .readerFor (ExtendableBean.class) .readValue (json); assertEquals ("שעועית שלי", שעועית שם); assertEquals ("val2", bean.getProperties (). get ("attr2")); }

3.4. @JsonSetter

@JsonSetter מהווה אלטרנטיבה ל @JsonProperty המסמן את השיטה כשיטת קובע.

זה מאוד שימושי כשאנחנו צריכים לקרוא כמה נתונים של JSON, אבל מחלקת יישות היעד לא בדיוק תואמת את הנתונים האלהולכן עלינו לכוון את התהליך כך שיתאים.

בדוגמה הבאה, נפרט את השיטה setTheName () כקובע של שֵׁם נכס שלנו MyBean יֵשׁוּת:

מחלקה ציבורית MyBean {מזהה ציבורי אינטנסיבי; שם מחרוזת פרטי; @JsonSetter ("שם") public void setTheName (שם מחרוזת) {this.name = שם; }}

עכשיו כשאנחנו צריכים לבטל את הרישום של נתוני JSON, זה עובד בצורה מושלמת:

@ מבחן פומבי בטל כאשרDererializingUsingJsonSetter_thenCorrect () זורק IOException {String json = "{\" id \ ": 1, \" name \ ": \" שעועית שלי \ "}"; שעועית MyBean = ObjectMapper חדש () .readerFor (MyBean.class) .readValue (json); assertEquals ("השעועית שלי", bean.getTheName ()); }

3.5. @JsonDeserialize

@JsonDeserialize מציין את השימוש במכשיר deserializer מותאם אישית.

ראשית, נשתמש @JsonDeserialize לבטל את הערעור של תאריך אירוע נכס עם CustomDateDeserializer:

class class EventWithSerializer {שם מחרוזת ציבורי; @JsonDeserialize (באמצעות = CustomDateDeserializer.class) תאריך ציבורי eventDate; }

הנה הסרת ההתאמה המותאמת אישית:

מחלקה ציבורית CustomDateDeserializer מרחיב את StdDeserializer {פרטי סטטי SimpleDateFormat מעצב = חדש SimpleDateFormat ("dd-MM-yyyy hh: mm: ss"); ציבורי CustomDateDeserializer () {this (null); } CustomDateDeserializer ציבורי (Class vc) {super (vc); } @Override ציבורי deserialize תאריך (JsonParser jsonparser, DeserializationContext הקשר) זורק IOException {תאריך מחרוזת = jsonparser.getText (); נסה {return formatter.parse (תאריך); } לתפוס (ParseException e) {לזרוק RuntimeException (e) חדש; }}}

להלן מבחן גב אל גב:

@ מבחן ציבורי בטל כאשרDeserializingUsingJsonDeserialize_thenCorrect () זורק IOException {String json = "{" name ":" party "," eventDate ":" 20-12-2014 02:30:00 "}"; SimpleDateFormat df = SimpleDateFormat חדש ("dd-MM-yyyy hh: mm: ss"); EventWithSerializer event = ObjectMapper new () .readerFor (EventWithSerializer.class) .readValue (json); assertEquals ("20-12-2014 02:30:00", df.format (event.eventDate)); }

3.6. @JsonAlias

ה @JsonAlias מגדיר שם אחד או יותר חלופי עבור נכס במהלך עריקת ערעור.

בואו נראה איך הערה זו עובדת עם דוגמה מהירה:

מחלקה ציבורית AliasBean {@JsonAlias ​​({"fName", "f_name"}) פרטי מחרוזת שם פרטי; שם משפחה פרטי מחרוזת; }

הנה לנו POJO, ואנחנו רוצים לבטל את ערכת JSON עם ערכים כגון fName, f_name, ו שם פרטי לתוך ה שם פרטי משתנה של ה- POJO.

להלן מבחן המוודא שההערה הזו פועלת כצפוי:

@ מבחן ציבורי בטל כאשרDererializingUsingJsonAlias_thenCorrect () זורק IOException {String json = "{\" fName \ ": \" John \ ", \" lastName \ ": \" Green \ "}"; AliasBean aliasBean = ObjectMapper חדש (). ReaderFor (AliasBean.class) .readValue (json); assertEquals ("John", aliasBean.getFirstName ()); }

4. הערות על הכללת נכסים

4.1. @JsonIgnoreProperties

@JsonIgnoreProperties היא הערה ברמה כיתתית המסמנת נכס או רשימת נכסים שג'קסון יתעלם מהם.

בואו נסתכל על דוגמה מהירה להתעלמות מהנכס תְעוּדַת זֶהוּת מסידור:

@JsonIgnoreProperties ({"id"}) מעמד ציבורי BeanWithIgnore {public int id; שם מחרוזת ציבורי; }

עכשיו הנה המבחן שמוודא שההתעלמות מתרחשת:

@ מבחן ציבורי בטל כאשר SerializingUsingJsonIgnoreProperties_thenCorrect () זורק את JsonProcessingException {BeanWithIgnore bean = new BeanWithIgnore (1, "שעועית שלי"); תוצאת מחרוזת = ObjectMapper חדש () .writeValueAsString (שעועית); assertThat (תוצאה, containString ("השעועית שלי")); assertThat (תוצאה, לא (containString ("id"))); }

כדי להתעלם מכל מאפיין לא ידוע בקלט JSON ללא יוצא מן הכלל, אנו יכולים להגדיר ignoreUnknown = נכון שֶׁל @JsonIgnoreProperties ביאור.

4.2. @JsonIgnore

לעומת זאת, ה @JsonIgnore הערה משמשת לסימון מאפיין שיש להתעלם ממנו ברמת השדה.

בואו נשתמש @JsonIgnore להתעלם מהנכס תְעוּדַת זֶהוּת מסידור:

מחלקה ציבורית BeanWithIgnore {@JsonIgnore ID ID; שם מחרוזת ציבורי; }

ואז נבדוק כדי לוודא זאת תְעוּדַת זֶהוּת התעלם בהצלחה:

@ מבחן ציבורי בטל כאשר SerializingUsingJsonIgnore_thenCorrect () זורק JsonProcessingException {BeanWithIgnore שעועית = חדש BeanWithIgnore (1, "השעועית שלי"); תוצאת מחרוזת = ObjectMapper חדש () .writeValueAsString (שעועית); assertThat (תוצאה, containString ("השעועית שלי")); assertThat (תוצאה, לא (containString ("id"))); }

4.3. @JsonIgnoreType

@JsonIgnoreType מסמן את כל המאפיינים מסוג הערה שיש להתעלם מהם.

אנו יכולים להשתמש בהערה לסימון כל מאפייני הסוג שֵׁם להתעלם:

מחלקה ציבורית משתמש {מזהה אינטליגנטי; שם ציבורי; @JsonIgnoreType מחלקה סטטית ציבורית שם {public String firstName; שם משפחה ציבורי; }}

אנחנו יכולים גם לבדוק כדי לוודא שההתעלמות פועלת כראוי:

@ מבחן ציבורי בטל כאשר SerializingUsingJsonIgnoreType_thenCorrect () זורק את JsonProcessingException, ParseException {User.Name name = New User.Name ("John", "Doe"); משתמש משתמש = משתמש חדש (1, שם); תוצאת מחרוזת = ObjectMapper חדש () .writeValueAsString (משתמש); assertThat (תוצאה, containString ("1")); assertThat (תוצאה, לא (containString ("שם"))); assertThat (תוצאה, לא (containString ("ג'ון"))); }

4.4. @JsonInclude

אנחנו יכולים להשתמש @JsonInclude כדי לא לכלול מאפיינים עם ערכים ריקים / null / ברירת מחדל.

בואו נסתכל על דוגמה שאינה אפסים מסידור:

@JsonInclude (Include.NON_NULL) מחלקה ציבורית MyBean {ID מזהה ציבורי; שם מחרוזת ציבורי; }

הנה המבחן המלא:

חלל ציבורי כאשרSerializingUsingJsonInclude_thenCorrect () זורק JsonProcessingException {שעועית MyBean = MyBean חדש (1, null); תוצאת מחרוזת = ObjectMapper חדש () .writeValueAsString (שעועית); assertThat (תוצאה, containString ("1")); assertThat (תוצאה, לא (containString ("שם"))); }

4.5. @JsonAutoDetect

@JsonAutoDetect יכול לעקוף את סמנטיקה ברירת המחדל של אילו מאפיינים גלויים ואילו לא.

ראשית, בואו נסתכל כיצד ההערה יכולה לעזור מאוד בעזרת דוגמה פשוטה; בואו נאפשר סדר תכונות פרטיות:

@JsonAutoDetect (fieldVisibility = Visibility.ANY) מחלקה ציבורית PrivateBean {מזהה פרטי פרטי; שם מחרוזת פרטי; }

ואז המבחן:

@ מבחן ציבורי בטל כאשר SerializingUsingJsonAutoDetect_thenCorrect () זורק JsonProcessingException {שעועית PrivateBean = PrivateBean חדש (1, "השעועית שלי"); תוצאת מחרוזת = ObjectMapper חדש () .writeValueAsString (שעועית); assertThat (תוצאה, containString ("1")); assertThat (תוצאה, containString ("השעועית שלי")); }

5. ביאורים לטיפול בג'קסון פולימורפי

הבא בואו נסתכל על הערות הטיפול הפולימורפיות של ג'קסון:

  • @JsonTypeInfo - מציין פרטים על איזה סוג מידע לכלול בסידור
  • @JsonSubTypes - מציין תת-סוגים מהסוג המבואר
  • @JsonTypeName - מגדיר שם סוג לוגי לשימוש במחלקה המאושרת

בואו נבחן דוגמה מורכבת יותר ונשתמש בשלושתן - @JsonTypeInfo, @JsonSubTypes, ו @JsonTypeName - לערוך סדר / ייצור סדר של היישות גַן חַיוֹת:

גן חיות ציבורי {חיה ציבורית ציבורית; @JsonTypeInfo (use = JsonTypeInfo.Id.NAME, include = As.PROPERTY, property = "type") @JsonSubTypes ({@ JsonSubTypes.Type (value = Dog.class, name = "dog"), @ JsonSubTypes.Type ( value = Cat.class, name = "cat")}) class static public Animal {public שם מחרוזת; } @JsonTypeName ("כלב") מעמד סטטי ציבורי כלב מאריך את בעלי החיים {ציבוריים barkVolume; } @JsonTypeName ("חתול") מעמד סטטי ציבורי חתול מרחיב בעלי חיים {בוליאני לייקקרים; חיי אינטרס ציבוריים; }}

כשאנחנו מבצעים סידור:

@ מבחן ציבורי בטל כאשר SerializingPolymorphic_thenCorrect () זורק את JsonProcessingException {כלב Zoo.Dog = Zoo.Dog חדש ("תחרה"); גן חיות גן חיות = גן חיות חדש (כלב); תוצאת מחרוזת = ObjectMapper חדש () .writeValueAsString (גן חיות); assertThat (תוצאה, containString ("סוג")); assertThat (תוצאה, containString ("כלב")); }

הנה מה שמסדרת את סדרת גַן חַיוֹת למשל עם כֶּלֶב יביא ל:

{"animal": {"type": "dog", "name": "lacy", "barkVolume": 0}}

עכשיו להסרת סדרות. נתחיל עם קלט JSON הבא:

{"animal": {"name": "lacy", "type": "cat"}}

אז בואו נראה איך זה לא מסתדר לא גַן חַיוֹת למשל:

@ מבחן ציבורי בטל כאשרDeserializingPolymorphic_thenCorrect () זורק IOException {String json = "{\" animal \ ": {\" name \ ": \" lacy \ ", \" type \ ": \" cat \ "}}"; גן חיות גן חיות = ObjectMapper חדש () .readerFor (Zoo.class) .readValue (json); assertEquals ("lacy", zoo.animal.name); assertEquals (Zoo.Cat.class, zoo.animal.getClass ()); }

6. הערות כלליות של ג'קסון

הבא נדון בכמה מההערות הכלליות יותר של ג'קסון.

6.1. @JsonProperty

אנחנו יכולים להוסיף ה @JsonProperty ביאור לציין את שם הנכס ב- JSON.

בואו נשתמש @JsonProperty לסידור / לבטל את סדר הערך של הנכס שֵׁם כשאנחנו עוסקים בגטרים וקובעים לא סטנדרטיים:

מחלקה ציבורית MyBean {מזהה ציבורי אינטנסיבי; שם מחרוזת פרטי; @JsonProperty ("שם") set public spaceTheThe (שם מחרוזת) {this.name = שם; } @JsonProperty ("שם") מחרוזת ציבורית getTheName () {שם החזרה; }}

הבא המבחן שלנו:

@ מבחן ציבורי בטל כאשרUsingJsonProperty_thenCorrect () זורק IOException {שעועית MyBean = MyBean חדש (1, "שעועית שלי"); תוצאת מחרוזת = ObjectMapper חדש (). WriteValueAsString (שעועית); assertThat (תוצאה, containString ("השעועית שלי")); assertThat (תוצאה, containString ("1")); MyBean resultBean = ObjectMapper חדש () .readerFor (MyBean.class) .readValue (תוצאה); assertEquals ("השעועית שלי", resultBean.getTheName ()); }

6.2. @JsonFormat

ה @JsonFormat ביאור מציין פורמט בעת סדרת ערכי תאריך / שעה.

בדוגמה הבאה אנו משתמשים @JsonFormat כדי לשלוט על פורמט הנכס תאריך אירוע:

class class EventWithFormat {שם מחרוזת ציבורי; @JsonFormat (צורה = JsonFormat.Shape.STRING, תבנית = "dd-MM-yyyy hh: mm: ss") ציבורי תאריך eventDate; }

אז הנה המבחן:

@Test הציבור בטל כאשרSerializingUsingJsonFormat_thenCorrect () זורק JsonProcessingException, ParseException {SimpleDateFormat df = חדש SimpleDateFormat ("dd-MM-yyyy hh: mm: ss"); df.setTimeZone (TimeZone.getTimeZone ("UTC")); מחרוזת toParse = "20-12-2014 02:30:00"; תאריך תאריך = df.parse (toParse); EventWithFormat event = new EventWithFormat ("מסיבה", תאריך); תוצאת מחרוזת = ObjectMapper חדש (). WriteValueAsString (אירוע); assertThat (תוצאה, containString (toParse)); }

6.3. @JsonUnpacked

@JsonUnpacked מגדיר ערכים שיש לפתוח / לשטח אותם בעת סיווג / עריכה מחדש.

בואו נראה בדיוק איך זה עובד; נשתמש בהערה כדי לפרק את הנכס שֵׁם:

מחלקה ציבורית UnwrappedUser {מזהה אינטליגנטי; @JsonUnprap שם ציבורי; מחלקה סטטית ציבורית שם {public String firstName; שם משפחה ציבורי; }}

עכשיו בואו בואו לסדר מופע של הכיתה הזו:

@ מבחן פומבי בטל כאשר SerializingUsingJsonUnwrapped_thenCorrect () זורק את JsonProcessingException, ParseException {UnwrappedUser.Name name = new UnwrappedUser.Name ("John", "Doe"); UnwrappedUser user = חדש UnwrappedUser (1, שם); תוצאת מחרוזת = ObjectMapper חדש (). WriteValueAsString (משתמש); assertThat (תוצאה, containString ("ג'ון")); assertThat (תוצאה, לא (containString ("שם"))); }

לבסוף, הנה איך נראית התפוקה - שדות המחלקה המקוננת הסטטית נפרשים יחד עם השדה האחר:

{"id": 1, "firstName": "John", "lastName": "Doe"}

6.4. @JsonView

@JsonView מציין את התצוגה המפורטת בה ייכלל המאפיין לצורך סידור / עריכת סדר.

לדוגמה, נשתמש @JsonView לסדר מופע של פריט יֵשׁוּת.

ראשית, נתחיל בתצוגות:

מעמד ציבורי צפיות {מחלקה סטטית ציבורית ציבורית {} מעמד סטטי ציבורי פנימי מרחיב ציבורי {}}

הבא הנה פריט ישות המשתמשת בתצוגות:

פריט בכיתה ציבורית {@JsonView (Views.Public.class) מזהה מידע ציבורי; @JsonView (Views.Public.class) פריט מחרוזת itemName; @JsonView (Views.Internal.class) בעל מחרוזות ציבורי; }

לבסוף, המבחן המלא:

@ מבחן פומבי בטל כאשר SerializingUsingJsonView_thenCorrect () זורק JsonProcessingException {פריט פריט = פריט חדש (2, "ספר", "ג'ון"); תוצאת מחרוזת = ObjectMapper חדש () .writerWithView (Views.Public.class) .writeValueAsString (פריט); assertThat (תוצאה, containString ("ספר")); assertThat (תוצאה, containString ("2")); assertThat (תוצאה, לא (containString ("ג'ון"))); }

6.5. @JsonManagedReference, @JsonBackReference

ה @JsonManagedReference ו @JsonBackReference ביאורים יכולים לטפל ביחסי הורים וילדים ולעבוד סביב לולאות.

בדוגמה הבאה אנו משתמשים @JsonManagedReference ו @JsonBackReference לסדר את שלנו ItemWithRef יֵשׁוּת:

מחלקה ציבורית ItemWithRef {id מזהה ציבורי; public String itemName; @JsonManagedReference בעל UserWithRef ציבורי; }

שֶׁלָנוּ UserWithRef יֵשׁוּת:

מחלקה ציבורית UserWithRef {מזהה אינטליגנטי; שם מחרוזת ציבורי; @JsonBackReference רשימת משתמשים פריטי משתמש; }

ואז המבחן:

@ מבחן פומבי בטל כאשר SerializingUsingJacksonReferenceAnnotation_thenCorrect () זורק את JsonProcessingException {UserWithRef user = UserWithRef new (1, "John"); פריט ItemWithRef = ItemWithRef חדש (2, "ספר", משתמש); user.addItem (פריט); תוצאת מחרוזת = ObjectMapper חדש (). WriteValueAsString (פריט); assertThat (תוצאה, containString ("ספר")); assertThat (תוצאה, containString ("ג'ון")); assertThat (תוצאה, לא (containString ("userItems"))); }

6.6. @JsonIdentityInfo

@JsonIdentityInfo מציין שיש להשתמש בזהות אובייקט בעת סדרת ערכים / עריכת ערכים שלהם, כמו למשל בהתמודדות עם סוגים אינסופיים של בעיות רקורסיות.

בדוגמה הבאה יש לנו ItemWithIdentity ישות עם מערכת יחסים דו כיוונית עם UserWithIdentity יֵשׁוּת:

@JsonIdentityInfo (generator = ObjectIdGenerators.PropertyGenerator.class, property = "id") מחלקה ציבורית ItemWithIdentity {id מזהה ציבורי; פריט מחרוזת itemName; בעל UserWithIdentity ציבורי; }

ה UserWithIdentity יֵשׁוּת:

@JsonIdentityInfo (מחולל = ObjectIdGenerators.PropertyGenerator.class, property = "id") מחלקה ציבורית UserWithIdentity {id מזהה ציבורי; שם מחרוזת ציבורי; רשימת משתמשים UserItems; }

עַכשָׁיו בואו נראה איך מטפלים בבעיית הרקורסיה האינסופית:

@ מבחן פומבי בטל כאשר SerializingUsingJsonIdentityInfo_thenCorrect () זורק את JsonProcessingException {UserWithIdentity user = UserWithIdentity new (1, "John"); פריט ItemWithIdentity = ItemWithIdentity חדש (2, "ספר", משתמש); user.addItem (פריט); תוצאת מחרוזת = ObjectMapper חדש (). WriteValueAsString (פריט); assertThat (תוצאה, containString ("ספר")); assertThat (תוצאה, containString ("ג'ון")); assertThat (תוצאה, containString ("userItems")); }

הנה הפלט המלא של הפריט והמשתמש בסידרה:

{"id": 2, "itemName": "book", "owner": {"id": 1, "name": "John", "userItems": [2]}}

6.7. @JsonFilter

ה @JsonFilter ביאור מציין פילטר לשימוש במהלך סדרת סדר.

ראשית, אנו מגדירים את הישות ומצביעים על המסנן:

@JsonFilter ("myFilter") מעמד ציבורי BeanWithFilter {id מזהה ציבורי; שם מחרוזת ציבורי; }

כעת בבדיקה המלאה אנו מגדירים את המסנן, שאינו כולל את כל המאפיינים האחרים למעט שֵׁם מסידור:

@ מבחן פומבי בטל כאשר SerializingUsingJsonFilter_thenCorrect () זורק JsonProcessingException {שעועית BeanWithFilter = BeanWithFilter חדש (1, "שעועית שלי"); FilterProvider filters = חדש SimpleFilterProvider (). AddFilter ("myFilter", SimpleBeanPropertyFilter.filterOutAllExcept ("שם")); תוצאת מחרוזת = ObjectMapper חדש () .writer (פילטרים) .writeValueAsString (שעועית); assertThat (תוצאה, containString ("השעועית שלי")); assertThat (תוצאה, לא (containString ("id"))); }

7. ביאור ג'קסון בהתאמה אישית

בשלב הבא נראה כיצד ליצור ביאור מותאם אישית לג'קסון. אנחנו יכולים לעשות שימוש ב- @JacksonAnnotationsInside ביאור:

@Retention (RetentionPolicy.RUNTIME) @JacksonAnnotationsInside @JsonInclude (Include.NON_NULL) @JsonPropertyOrder ({"name", "id", "dateCreated"}) Public @ ממשק CustomAnnotation {}

עכשיו אם נשתמש בהערה החדשה על ישות:

@CustomAnnotation מחלקה ציבורית BeanWithCustomAnnotation {id מזהה ציבורי; שם מחרוזת ציבורי; תאריך תאריך ציבורי נוצר; }

אנו יכולים לראות כיצד הוא משלב את ההערות הקיימות למנהג פשוט, בו אנו יכולים להשתמש בקיצור:

@ מבחן פומבי בטל כאשר SerializingUsingCustomAnnotation_thenCorrect () זורק JsonProcessingException {BeanWithCustomAnnotation שעועית = חדש BeanWithCustomAnnotation (1, "שעועית שלי", null); תוצאת מחרוזת = ObjectMapper חדש (). WriteValueAsString (שעועית); assertThat (תוצאה, containString ("השעועית שלי")); assertThat (תוצאה, containString ("1")); assertThat (תוצאה, לא (containString ("dateCreated"))); }

תפוקת תהליך הסידור:

{"name": "השעועית שלי", "id": 1}

8. הערות ג'קסון מיקס

בשלב הבא נראה כיצד להשתמש בהערות ג'קסון מיקס.

לדוגמה, בואו נשתמש בהערות MixIn כדי להתעלם ממאפייני הסוג מִשׁתַמֵשׁ:

מחלקה ציבורית פריט {מזהה ציבורי; public String itemName; בעל משתמש ציבורי; }
מחלקה ציבורית @JsonIgnoreType MyMixInForIgnoreType {}

אז בואו נראה את זה בפעולה:

@ מבחן פומבי בטל כאשר SerializingUsingMixInAnnotation_thenCorrect () זורק JsonProcessingException {פריט פריט = פריט חדש (1, "ספר", null); תוצאת מחרוזת = ObjectMapper חדש (). WriteValueAsString (פריט); assertThat (תוצאה, containString ("בעלים")); ממפה ObjectMapper = ObjectMapper חדש (); mapper.addMixIn (User.class, MyMixInForIgnoreType.class); תוצאה = mapper.writeValueAsString (פריט); assertThat (תוצאה, לא (containString ("בעלים"))); }

9. השבת את ההערה של ג'קסון

לבסוף, בואו נראה איך אנחנו יכולים השבת את כל ההערות של ג'קסון. אנו יכולים לעשות זאת על ידי השבתת ה- MapperFeature.USE_ANNOTATIONS כמו בדוגמה הבאה:

@JsonInclude (Include.NON_NULL) @JsonPropertyOrder ({"name", "id"}) מחלקה ציבורית MyBean {id public public; שם מחרוזת ציבורי; }

כעת, לאחר השבתת ההערות, לא אמורה להיות לכך השפעה ועל ברירות המחדל של הספרייה לחול:

@ מבחן ציבורי בטל כאשר DisisAllAnnotations_thenAllDisabled () זורק IOException {שעועית MyBean = MyBean חדש (1, null); ממפה ObjectMapper = ObjectMapper חדש (); mapper.disable (MapperFeature.USE_ANNOTATIONS); תוצאת מחרוזת = mapper.writeValueAsString (שעועית); assertThat (תוצאה, containString ("1")); assertThat (תוצאה, containString ("שם")); }

התוצאה של סידור לפני השבתת ההערות:

{"id": 1}

התוצאה של סדרת סדר לאחר ביטול ההערות:

{"id": 1, "name": null}

10. מסקנה

במאמר זה בחנו את ההערות של ג'קסון, רק מגרדים את פני השטח של סוג הגמישות שאנחנו יכולים לקבל על ידי שימוש נכון בהן.

ניתן למצוא את היישום של כל הדוגמאות וקטעי הקוד באתר GitHub.


$config[zx-auto] not found$config[zx-overlay] not found