From 9d326b55bc5436251c917ecb2c6ddb05493dc2ae Mon Sep 17 00:00:00 2001 From: Karsten Silz Date: Sun, 6 Sep 2020 13:23:34 +0100 Subject: [PATCH] BAEL-3326, "Optimizing JSON Schema for production use": More code for slim customer. --- .../CustomerDeserializer.java | 1 + .../jsonoptimization/CustomerShortNames.java | 1 + .../CustomerSlimDeserializer.java | 37 +++++++++ .../CustomerSlimSerializer.java | 28 +++++++ .../CustomerSlimShortNames.java | 81 +++++++++++++++++++ .../JsonOptimizationUnitTest.java | 57 ++++++++----- 6 files changed, 187 insertions(+), 18 deletions(-) create mode 100644 json/src/main/java/com/baeldung/jsonoptimization/CustomerSlimDeserializer.java create mode 100644 json/src/main/java/com/baeldung/jsonoptimization/CustomerSlimSerializer.java create mode 100644 json/src/main/java/com/baeldung/jsonoptimization/CustomerSlimShortNames.java diff --git a/json/src/main/java/com/baeldung/jsonoptimization/CustomerDeserializer.java b/json/src/main/java/com/baeldung/jsonoptimization/CustomerDeserializer.java index 04ab15556a..1815c5f202 100644 --- a/json/src/main/java/com/baeldung/jsonoptimization/CustomerDeserializer.java +++ b/json/src/main/java/com/baeldung/jsonoptimization/CustomerDeserializer.java @@ -43,6 +43,7 @@ public class CustomerDeserializer extends StdDeserializer { feedback.setPhoneNumber(phoneNumber.isNull() ? null : phoneNumber.asText()); JsonNode email = node.get(8); feedback.setEmail(email.isNull() ? null : email.asText()); + return feedback; } } diff --git a/json/src/main/java/com/baeldung/jsonoptimization/CustomerShortNames.java b/json/src/main/java/com/baeldung/jsonoptimization/CustomerShortNames.java index 2a47a4bbac..b94fbb1033 100644 --- a/json/src/main/java/com/baeldung/jsonoptimization/CustomerShortNames.java +++ b/json/src/main/java/com/baeldung/jsonoptimization/CustomerShortNames.java @@ -6,6 +6,7 @@ import com.fasterxml.jackson.annotation.JsonProperty; public class CustomerShortNames { + @JsonProperty("i") private long id; @JsonProperty("f") diff --git a/json/src/main/java/com/baeldung/jsonoptimization/CustomerSlimDeserializer.java b/json/src/main/java/com/baeldung/jsonoptimization/CustomerSlimDeserializer.java new file mode 100644 index 0000000000..9da7b7c873 --- /dev/null +++ b/json/src/main/java/com/baeldung/jsonoptimization/CustomerSlimDeserializer.java @@ -0,0 +1,37 @@ +package com.baeldung.jsonoptimization; + +import java.io.IOException; + +import com.fasterxml.jackson.core.JsonParser; +import com.fasterxml.jackson.core.ObjectCodec; +import com.fasterxml.jackson.databind.DeserializationContext; +import com.fasterxml.jackson.databind.JsonNode; +import com.fasterxml.jackson.databind.deser.std.StdDeserializer; + +public class CustomerSlimDeserializer extends StdDeserializer { + private static final long serialVersionUID = 1L; + + public CustomerSlimDeserializer() { + this(null); + } + + public CustomerSlimDeserializer(Class t) { + super(t); + } + + @Override + public CustomerSlim deserialize(JsonParser parser, DeserializationContext deserializer) throws IOException { + CustomerSlim feedback = new CustomerSlim(); + ObjectCodec codec = parser.getCodec(); + JsonNode node = codec.readTree(parser); + + feedback.setId(node.get(0) + .asLong()); + feedback.setName(node.get(1) + .asText()); + feedback.setAddress(node.get(2) + .asText()); + + return feedback; + } +} diff --git a/json/src/main/java/com/baeldung/jsonoptimization/CustomerSlimSerializer.java b/json/src/main/java/com/baeldung/jsonoptimization/CustomerSlimSerializer.java new file mode 100644 index 0000000000..520c541da6 --- /dev/null +++ b/json/src/main/java/com/baeldung/jsonoptimization/CustomerSlimSerializer.java @@ -0,0 +1,28 @@ +package com.baeldung.jsonoptimization; + +import java.io.IOException; + +import com.fasterxml.jackson.core.JsonGenerator; +import com.fasterxml.jackson.databind.SerializerProvider; +import com.fasterxml.jackson.databind.ser.std.StdSerializer; + +public class CustomerSlimSerializer extends StdSerializer { + private static final long serialVersionUID = 1L; + + public CustomerSlimSerializer() { + this(null); + } + + public CustomerSlimSerializer(Class t) { + super(t); + } + + @Override + public void serialize(CustomerSlim customer, JsonGenerator jsonGenerator, SerializerProvider serializer) throws IOException { + jsonGenerator.writeStartArray(); + jsonGenerator.writeNumber(customer.getId()); + jsonGenerator.writeString(customer.getName()); + jsonGenerator.writeString(customer.getAddress()); + jsonGenerator.writeEndArray(); + } +} diff --git a/json/src/main/java/com/baeldung/jsonoptimization/CustomerSlimShortNames.java b/json/src/main/java/com/baeldung/jsonoptimization/CustomerSlimShortNames.java new file mode 100644 index 0000000000..7bb20a7453 --- /dev/null +++ b/json/src/main/java/com/baeldung/jsonoptimization/CustomerSlimShortNames.java @@ -0,0 +1,81 @@ +package com.baeldung.jsonoptimization; + +import java.util.Objects; + +import com.fasterxml.jackson.annotation.JsonProperty; + +public class CustomerSlimShortNames { + + @JsonProperty("i") + private long id; + + @JsonProperty("n") + private String name; + + @JsonProperty("a") + private String address; + + public long getId() { + return id; + } + + public void setId(long id) { + this.id = id; + } + + public String getName() { + return name; + } + + public void setName(String name) { + this.name = name; + } + + public String getAddress() { + return address; + } + + public void setAddress(String address) { + this.address = address; + } + + @Override + public int hashCode() { + return Objects.hash(address, id, name); + } + + @Override + public boolean equals(Object obj) { + if (this == obj) { + return true; + } + if (!(obj instanceof CustomerSlimShortNames)) { + return false; + } + CustomerSlimShortNames other = (CustomerSlimShortNames) obj; + return Objects.equals(address, other.address) && id == other.id && Objects.equals(name, other.name); + } + + @Override + public String toString() { + return "CustomerSlim [id=" + id + ", name=" + name + ", address=" + address + "]"; + } + + public static CustomerSlimShortNames[] fromCustomers(Customer[] customers) { + CustomerSlimShortNames[] feedback = new CustomerSlimShortNames[customers.length]; + + for (int i = 0; i < customers.length; i++) { + Customer aCustomer = customers[i]; + CustomerSlimShortNames newOne = new CustomerSlimShortNames(); + + newOne.setId(aCustomer.getId()); + newOne.setName(aCustomer.getFirstName() + " " + aCustomer.getLastName()); + newOne.setAddress(aCustomer.getStreet() + ", " + aCustomer.getCity() + " " + aCustomer.getState() + " " + aCustomer.getPostalCode()); + + feedback[i] = newOne; + } + + return feedback; + } + +} diff --git a/json/src/test/java/com/baeldung/jsonoptimization/JsonOptimizationUnitTest.java b/json/src/test/java/com/baeldung/jsonoptimization/JsonOptimizationUnitTest.java index a1dbe08fed..dd5703543f 100644 --- a/json/src/test/java/com/baeldung/jsonoptimization/JsonOptimizationUnitTest.java +++ b/json/src/test/java/com/baeldung/jsonoptimization/JsonOptimizationUnitTest.java @@ -23,10 +23,12 @@ import com.fasterxml.jackson.databind.module.SimpleModule; class JsonOptimizationUnitTest { private static final String TEST_LABEL_DEFAULT_JSON = "Default JSON"; private static final String TEST_LABEL_DEFAULT_JSON_NO_NULL = "Default JSON without null"; - private static final String TEST_LABEL_SHORTER_ATTRIBUTE_NAMES = "Shorter Attribute Names"; - private static final String TEST_LABEL_SHORTER_ATTRIBUTE_NAMES_NO_NULL = "Shorter Attribute Names without null"; - private static final String TEST_LABEL_CUSTOM_SERIALIZER = "Custom Serializer"; + private static final String TEST_LABEL_SHORT_NAMES = "Shorter attribute names"; + private static final String TEST_LABEL_SHORT_NAMES_NO_NULL = "Shorter attribute names without null"; + private static final String TEST_LABEL_CUSTOM_SERIALIZER = "Custom serializer"; + private static final String TEST_LABEL_SLIM_CUSTOM_SERIALIZER = "Slim custom serializer"; private static final String TEST_LABEL_SLIM_CUSTOMER = "Slim customer"; + private static final String TEST_LABEL_SLIM_CUSTOMER_SHORT_NAMES = "Slim customer with shorter attribute names"; private static DecimalFormat LENGTH_FORMATTER = new DecimalFormat("###,###,###"); private static Customer[] customers; private ObjectMapper mapper; @@ -62,19 +64,19 @@ class JsonOptimizationUnitTest { } @Test - void testShorterAttributes() throws IOException { - printBanner(TEST_LABEL_SHORTER_ATTRIBUTE_NAMES); + void testShortNames() throws IOException { + printBanner(TEST_LABEL_SHORT_NAMES); CustomerShortNames[] shorterOnes = CustomerShortNames.fromCustomers(customers); - byte[] shorterJson = createPlainJson(TEST_LABEL_SHORTER_ATTRIBUTE_NAMES, shorterOnes); - compressJson(TEST_LABEL_SHORTER_ATTRIBUTE_NAMES, shorterJson); + byte[] shorterJson = createPlainJson(TEST_LABEL_SHORT_NAMES, shorterOnes); + compressJson(TEST_LABEL_SHORT_NAMES, shorterJson); } @Test - void testShorterAttributesNoNull() throws IOException { - printBanner(TEST_LABEL_SHORTER_ATTRIBUTE_NAMES_NO_NULL); + void testShortNamesNoNull() throws IOException { + printBanner(TEST_LABEL_SHORT_NAMES_NO_NULL); CustomerShortNamesNoNull[] shorterOnesNoNull = CustomerShortNamesNoNull.fromCustomers(customers); - byte[] shorterJson = createPlainJson(TEST_LABEL_SHORTER_ATTRIBUTE_NAMES_NO_NULL, shorterOnesNoNull); - compressJson(TEST_LABEL_SHORTER_ATTRIBUTE_NAMES_NO_NULL, shorterJson); + byte[] shorterJson = createPlainJson(TEST_LABEL_SHORT_NAMES_NO_NULL, shorterOnesNoNull); + compressJson(TEST_LABEL_SHORT_NAMES_NO_NULL, shorterJson); } @Test @@ -85,21 +87,40 @@ class JsonOptimizationUnitTest { compressJson(TEST_LABEL_SLIM_CUSTOMER, slimJson); } + @Test + void testSlimShortNames() throws IOException { + printBanner(TEST_LABEL_SLIM_CUSTOMER_SHORT_NAMES); + CustomerSlimShortNames[] slimOnes = CustomerSlimShortNames.fromCustomers(customers); + byte[] slimJson = createPlainJson(TEST_LABEL_SLIM_CUSTOMER_SHORT_NAMES, slimOnes); + compressJson(TEST_LABEL_SLIM_CUSTOMER_SHORT_NAMES, slimJson); + } + @Test void testCustomSerializer() throws IOException { printBanner(TEST_LABEL_CUSTOM_SERIALIZER); - - SimpleModule serializer = new SimpleModule("CustomCustomerSerializer", new Version(1, 0, 0, null, null, null)); + + SimpleModule serializer = new SimpleModule("CustomDeSerializer", new Version(1, 0, 0, null, null, null)); serializer.addSerializer(Customer.class, new CustomerSerializer()); + serializer.addDeserializer(Customer.class, new CustomerDeserializer()); mapper.registerModule(serializer); - - SimpleModule deserializer = new SimpleModule("CustomCustomerDeserializer", new Version(1, 0, 0, null, null, null)); - deserializer.addDeserializer(Customer.class, new CustomerDeserializer()); - mapper.registerModule(deserializer); - + byte[] plainJson = createPlainJson(TEST_LABEL_CUSTOM_SERIALIZER, customers); compressJson(TEST_LABEL_CUSTOM_SERIALIZER, plainJson); } + + @Test + void testSlimCustomSerializer() throws IOException { + printBanner(TEST_LABEL_SLIM_CUSTOM_SERIALIZER); + + SimpleModule serializer = new SimpleModule("SlimCustomDeSerializer", new Version(1, 0, 0, null, null, null)); + serializer.addSerializer(CustomerSlim.class, new CustomerSlimSerializer()); + serializer.addDeserializer(CustomerSlim.class, new CustomerSlimDeserializer()); + mapper.registerModule(serializer); + + CustomerSlim[] slimOnes = CustomerSlim.fromCustomers(customers); + byte[] plainJson = createPlainJson(TEST_LABEL_SLIM_CUSTOM_SERIALIZER, slimOnes); + compressJson(TEST_LABEL_SLIM_CUSTOM_SERIALIZER, plainJson); + } private void printBanner(String name) { System.out.println();