All Downloads are FREE. Search and download functionalities are using the official Maven repository.
Please wait. This can take some minutes ...
Many resources are needed to download a project. Please understand that we have to compensate our server costs. Thank you in advance.
Project price only 1 $
You can buy this project and download/modify it how often you want.
com.github.aidensuen.mongo.util.SerializationUtils Maven / Gradle / Ivy
package com.github.aidensuen.mongo.util;
import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.module.SimpleModule;
import com.github.aidensuen.mongo.jackson.CustomDateSerializer;
import com.github.aidensuen.mongo.jackson.CustomObjectDeserializer;
import com.mongodb.util.JSON;
import org.bson.Document;
import org.springframework.core.convert.converter.Converter;
import org.springframework.lang.Nullable;
import java.util.*;
/**
* Utility methods for JSON serialization.
*
* @author Oliver Gierke
* @author Christoph Strobl
* @author Mark Paluch
*/
public abstract class SerializationUtils {
private static ThreadLocal mapperThreadLocal = new ThreadLocal<>();
private static SimpleModule module = new SimpleModule();
static {
module.addSerializer(Date.class, new CustomDateSerializer());
module.addDeserializer(Object.class, new CustomObjectDeserializer());
}
private SerializationUtils() {
}
/**
* Flattens out a given {@link Document}.
*
*
*
* {
* _id : 1
* nested : { value : "conflux"}
* }
*
* will result in
*
* {
* _id : 1
* nested.value : "conflux"
* }
*
*
*
* @param source can be {@literal null}.
* @return {@link Collections#emptyMap()} when source is {@literal null}
* @since 1.8
*/
public static Map flattenMap(@Nullable Document source) {
if (source == null) {
return Collections.emptyMap();
}
Map result = new LinkedHashMap<>();
toFlatMap("", source, result);
return result;
}
private static void toFlatMap(String currentPath, Object source, Map map) {
if (source instanceof Document) {
Document document = (Document) source;
Iterator> it = document.entrySet().iterator();
String pathPrefix = currentPath.isEmpty() ? "" : currentPath + '.';
while (it.hasNext()) {
Map.Entry entry = it.next();
if (entry.getKey().startsWith("$")) {
if (map.containsKey(currentPath)) {
((Document) map.get(currentPath)).put(entry.getKey(), entry.getValue());
} else {
map.put(currentPath, new Document(entry.getKey(), entry.getValue()));
}
} else {
toFlatMap(pathPrefix + entry.getKey(), entry.getValue(), map);
}
}
} else {
map.put(currentPath, source);
}
}
/**
* Serializes the given object into pseudo-JSON meaning it's trying to create a JSON representation as far as possible
* but falling back to the given object's {@link Object#toString()} method if it's not serializable. Useful for
* printing raw {@link Document}s containing complex values before actually converting them into Mongo native types.
*
* @param value
* @return the serialized value or {@literal null}.
*/
@Nullable
public static String serializeToJsonSafely(@Nullable Object value, boolean ignoreNull) {
if (value == null) {
return null;
}
try {
return value instanceof Document ? ((Document) value).toJson() : JSON.serialize(value);
} catch (Exception e) {
if (value instanceof Collection) {
return toString((Collection) value, ignoreNull);
} else if (value instanceof Map) {
return toString((Map) value, ignoreNull);
} else {
if (mapperThreadLocal.get() == null){
ObjectMapper objectMapper = new ObjectMapper();
objectMapper.registerModules(module);
mapperThreadLocal.set(objectMapper);
}
if (ignoreNull) {
mapperThreadLocal.get().setSerializationInclusion(JsonInclude.Include.NON_NULL);
} else {
mapperThreadLocal.get().setSerializationInclusion(JsonInclude.Include.ALWAYS);
}
Document document = mapperThreadLocal.get().convertValue(value, Document.class);
return serializeToJsonSafely(document, true);
}
}
}
private static String toString(Map source, boolean ignoreNull) {
return iterableToDelimitedString(source.entrySet(), "{ ", " }",
entry -> String.format("\"%s\" : %s", entry.getKey(), serializeToJsonSafely(entry.getValue(), ignoreNull)));
}
private static String toString(Collection source, boolean ignoreNull) {
return iterableToDelimitedString(source, "[ ", " ]", sourc -> serializeToJsonSafely(sourc, ignoreNull));
}
/**
* Creates a string representation from the given {@link Iterable} prepending the postfix, applying the given
* {@link Converter} to each element before adding it to the result {@link String}, concatenating each element with
* {@literal ,} and applying the postfix.
*
* @param source
* @param prefix
* @param postfix
* @param transformer
* @return
*/
private static String iterableToDelimitedString(Iterable source, String prefix, String postfix,
Converter transformer) {
StringBuilder builder = new StringBuilder(prefix);
Iterator iterator = source.iterator();
while (iterator.hasNext()) {
builder.append(transformer.convert(iterator.next()));
if (iterator.hasNext()) {
builder.append(", ");
}
}
return builder.append(postfix).toString();
}
}