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.
net.n2oapp.framework.config.io.IOProcessorImpl Maven / Gradle / Ivy
package net.n2oapp.framework.config.io;
import net.n2oapp.framework.api.N2oNamespace;
import net.n2oapp.framework.api.StringUtils;
import net.n2oapp.framework.api.data.DomainProcessor;
import net.n2oapp.framework.api.exception.N2oException;
import net.n2oapp.framework.api.metadata.aware.IdAware;
import net.n2oapp.framework.api.metadata.aware.NamespaceUriAware;
import net.n2oapp.framework.api.metadata.io.*;
import net.n2oapp.framework.api.metadata.persister.NamespacePersister;
import net.n2oapp.framework.api.metadata.persister.NamespacePersisterFactory;
import net.n2oapp.framework.api.metadata.persister.TypedElementPersister;
import net.n2oapp.framework.api.metadata.reader.NamespaceReader;
import net.n2oapp.framework.api.metadata.reader.NamespaceReaderFactory;
import net.n2oapp.framework.api.metadata.reader.TypedElementReader;
import org.apache.commons.lang3.ArrayUtils;
import org.jdom2.Attribute;
import org.jdom2.Element;
import org.jdom2.Namespace;
import org.springframework.context.support.MessageSourceAccessor;
import org.springframework.core.env.PropertyResolver;
import java.lang.reflect.Array;
import java.util.*;
import java.util.function.BiConsumer;
import java.util.function.Consumer;
import java.util.function.Function;
import java.util.function.Supplier;
import static java.util.Objects.isNull;
import static java.util.Objects.nonNull;
import static org.apache.commons.lang3.StringUtils.isEmpty;
import static org.springframework.util.StringUtils.hasText;
/**
* Реализация процессора считывания и записи DOM элементов
*/
public final class IOProcessorImpl implements IOProcessor {
/**
* Если true, то чтение, false запись
*/
private final boolean r;
private NamespaceReaderFactory readerFactory;
private NamespacePersisterFactory persisterFactory;
private MessageSourceAccessor messageSourceAccessor;
private PropertyResolver systemProperties;
private boolean failFast = true;
private final DomainProcessor domainProcessor = new DomainProcessor();
public IOProcessorImpl(boolean read) {
this.r = read;
}
public IOProcessorImpl(NamespaceReaderFactory readerFactory) {
this.r = true;
this.readerFactory = readerFactory;
if (readerFactory instanceof IOProcessorAware)
((IOProcessorAware) readerFactory).setIOProcessor(this);
}
public IOProcessorImpl(NamespacePersisterFactory persisterFactory) {
this.r = false;
this.persisterFactory = persisterFactory;
if (persisterFactory instanceof IOProcessorAware)
((IOProcessorAware) persisterFactory).setIOProcessor(this);
}
@Override
public void read(Element element, T entity, BiConsumer reader) {
if (r) {
reader.accept(element, entity);
}
}
@Override
public void persist(T entity, Element element, BiConsumer persister) {
if (!r) {
persister.accept(entity, element);
}
}
@Override
public void child(Element element, String sequences, String childName,
Supplier extends T> getter, Consumer super T> setter,
TypedElementIO io) {
if (r) {
Element child;
if (sequences != null) {
child = element.getChild(sequences, element.getNamespace());
if (child == null)
return;
} else {
child = element;
}
child = child.getChild(childName, element.getNamespace());
if (child != null) {
setter.accept(read(io, child));
}
} else {
T entity = getter.get();
if (entity != null) {
Element seqE = element;
if (sequences != null) {
seqE = initSequenceElement(element, sequences);
}
Element childE = persist(io, entity, element.getNamespace());
installNamespace(childE, element.getNamespace());
seqE.addContent(childE);
}
}
}
@Override
public void child(Element element, String sequences, String childName,
Supplier getter, Consumer setter,
Class elementClass, ElementIO io) {
child(element, sequences, childName, getter, setter, new TypedElementIO() {
@Override
public Class getElementClass() {
return elementClass;
}
@Override
public void io(Element e, T t, IOProcessor p) {
io.io(e, t, p);
}
@Override
public String getElementName() {
return childName;
}
});
}
@Override
public void child(Element element, String sequences, String childName,
Supplier extends T> getter, Consumer super T> setter,
Supplier extends T> newInstance, ElementIO io) {
child(element, sequences, childName, getter, setter, new TypedElementIO() {
private Class elementClass;
@Override
public String getElementName() {
return childName;
}
@Override
public Class getElementClass() {
if (elementClass == null)
throw new IllegalStateException("you shall first to call #newInstance(Element)");
return elementClass;
}
@Override
public T newInstance(Element element) {
T entity = newInstance.get();
if (elementClass == null)
elementClass = (Class) entity.getClass();
return entity;
}
@Override
public void io(Element e, T t, IOProcessor p) {
io.io(e, t, p);
}
});
}
@Override
public ,
P extends TypedElementPersister super T>> void anyChild(Element element, String sequences,
Supplier extends T> getter, Consumer super T> setter,
ElementIOFactory factory) {
if (r) {
Element seqE;
if (sequences != null) {
seqE = element.getChild(sequences, element.getNamespace());
if (seqE == null) return;
} else {
seqE = element;
}
for (Object child : seqE.getChildren()) {
Element childE = (Element) child;
setter.accept(read(factory, childE));
}
} else {
T entity = getter.get();
if (entity == null) return;
Element seqE;
if (sequences != null) {
seqE = initSequenceElement(element, sequences);
} else {
seqE = element;
}
Element childE = persist(factory, entity, element.getNamespace());
if (childE != null) {
installNamespace(childE, element.getNamespace());
seqE.addContent(childE);
}
}
}
@Override
public ,
P extends NamespacePersister super T>> void anyChild(Element element, String sequences,
Supplier getter, Consumer setter,
NamespaceIOFactory factory,
Namespace defaultNamespace) {
if (r) {
Element seqE;
if (sequences != null) {
seqE = element.getChild(sequences, element.getNamespace());
if (seqE == null) return;
} else {
seqE = element;
}
for (Object child : seqE.getChildren()) {
Element childE = (Element) child;
T childT = read(factory, childE, seqE.getNamespace(), defaultNamespace);
if (childT != null) {
setter.accept(childT);
return;
}
}
} else {
T entity = getter.get();
if (entity == null) return;
Element seqE;
if (sequences != null) {
seqE = initSequenceElement(element, sequences);
} else {
seqE = element;
}
Element childE = persist(factory, entity, seqE.getNamespace(), defaultNamespace);
if (childE != null) {
installNamespace(childE, element.getNamespace());
seqE.addContent(childE);
}
}
}
@Override
@SuppressWarnings("unchecked")
public void children(Element element, String sequences, String childrenName,
Supplier getter, Consumer setter,
TypedElementIO io) {
if (r) {
List result = new ArrayList<>();
Element seqE;
if (sequences != null) {
seqE = element.getChild(sequences, element.getNamespace());
if (seqE == null) return;
} else {
seqE = element;
}
for (Object child : seqE.getChildren(childrenName, seqE.getNamespace())) {
Element childE = (Element) child;
T entity = read(io, childE);
result.add(entity);
}
if (result.size() > 0) {
T[] res = (T[]) Array.newInstance(io.getElementClass(), result.size());
res = result.toArray(res);
setter.accept(res);
}
} else {
T[] entity = getter.get();
if (entity == null) return;
Element seqE;
if (sequences != null) {
seqE = initSequenceElement(element, sequences);
} else {
seqE = element;
}
for (T child : entity) {
Element childE = persist(io, child, seqE.getNamespace());
installNamespace(childE, seqE.getNamespace());
seqE.addContent(childE);
}
}
}
@Override
@SuppressWarnings("unchecked")
public void childrenToMap(Element element, String sequences, String childrenName,
String keyName, String valueName,
Supplier> getter, Consumer> setter) {
if (r) {
Map result = new HashMap<>();
Element seqE;
if (sequences != null) {
seqE = element.getChild(sequences, element.getNamespace());
if (seqE == null) return;
} else {
seqE = element;
}
for (Object child : seqE.getChildren(childrenName, seqE.getNamespace())) {
Element childE = (Element) child;
String key = process(childE.getAttribute(keyName).getValue());
String value = valueName == null ?
childE.getValue() :
childE.getAttribute(valueName).getValue();
Object objValue = domainProcessor.deserialize(value, (String) null);
result.put(key, objValue);
}
setter.accept(result);
} else {
persistChildrenMap(element, sequences, childrenName, keyName, valueName, getter);
}
}
@Override
public void childrenAttributesToMap(Element element, String sequences, String childrenName,
Supplier> getter, Consumer> setter) {
if (r) {
Map result = new HashMap<>();
Element seqE;
if (sequences != null) {
seqE = element.getChild(sequences, element.getNamespace());
if (seqE == null) return;
} else {
seqE = element;
}
for (Object child : seqE.getChildren(childrenName, seqE.getNamespace())) {
Element childE = (Element) child;
Attribute attribute = childE.getAttributes().get(0);
String key = attribute.getName();
String value = attribute.getValue();
Object objValue = domainProcessor.deserialize(value);
result.put(key, objValue);
}
setter.accept(result);
} else {
Map values = getter.get();
if (values == null) return;
Element seqE;
seqE = persistSequences(element, sequences);
for (String k : values.keySet()) {
Element childE = new Element(childrenName, element.getNamespace());
childE.setAttribute(k, values.get(k).toString());
seqE.addContent(childE);
}
}
}
@Override
@SuppressWarnings("unchecked")
public void childrenToStringMap(Element element, String sequences, String childrenName,
String keyName, String valueName,
Supplier> getter, Consumer> setter) {
if (r) {
Map result = new HashMap<>();
Element seqE;
if (sequences != null) {
seqE = element.getChild(sequences, element.getNamespace());
if (seqE == null) return;
} else {
seqE = element;
}
for (Object child : seqE.getChildren(childrenName, seqE.getNamespace())) {
Element childE = (Element) child;
String key = null;
if (childE.getAttribute(keyName) != null)
key = process(childE.getAttribute(keyName).getValue());
String value = valueName == null ?
childE.getValue() :
childE.getAttribute(valueName).getValue();
result.put(key, value);
}
setter.accept(result);
} else {
persistChildrenMap(element, sequences, childrenName, keyName, valueName, getter);
}
}
@Override
@SuppressWarnings("unchecked")
public void childrenToStringArray(Element element, String sequences, String childrenName,
Supplier getter, Consumer setter) {
if (r) {
List result = new ArrayList<>();
Element seqE;
if (sequences != null) {
seqE = element.getChild(sequences, element.getNamespace());
if (seqE == null) return;
} else {
seqE = element;
}
for (Object child : seqE.getChildren(childrenName, seqE.getNamespace())) {
Element childE = (Element) child;
String value = process(childE.getValue());
result.add(value);
}
if (!result.isEmpty()) {
String[] res = new String[result.size()];
setter.accept(result.toArray(res));
}
} else {
String[] values = getter.get();
if (values == null) return;
Element seqE;
seqE = persistSequences(element, sequences);
for (String k : values) {
Element childE = new Element(childrenName, element.getNamespace());
childE.setText(k);
seqE.addContent(childE);
}
}
}
private Element persistSequences(Element element, String sequences) {
Element seqE;
if (sequences != null) {
seqE = initSequenceElement(element, sequences);
} else {
seqE = element;
}
return seqE;
}
private void persistChildrenMap(Element element, String sequences, String childrenName,
String keyName, String valueName,
Supplier> getter) {
Map values = getter.get();
if (values == null) return;
Element seqE;
seqE = persistSequences(element, sequences);
for (String k : values.keySet()) {
Element childE = new Element(childrenName, element.getNamespace());
childE.setAttribute(keyName, k);
if (valueName == null) {
childE.setText(values.get(k).toString());
} else {
if (values.get(k) != null) {
childE.setAttribute(valueName, values.get(k).toString());
}
}
seqE.addContent(childE);
}
}
@Override
@SuppressWarnings("unchecked")
public void children(Element element, String sequences, String childrenName,
Supplier getter, Consumer setter,
Class elementClass, ElementIO io) {
children(element, sequences, childrenName, getter, setter, new TypedElementIO() {
@Override
public String getElementName() {
return childrenName;
}
@Override
public Class getElementClass() {
return elementClass;
}
@Override
public void io(Element e, T t, IOProcessor p) {
io.io(e, t, p);
}
});
}
@Override
@SuppressWarnings("unchecked")
public void children(Element element, String sequences, String childrenName,
Supplier getter, Consumer setter,
Supplier newInstance, ElementIO io) {
children(element, sequences, childrenName, getter, setter, new TypedElementIO() {
private Class elementClass;
@Override
public String getElementName() {
return childrenName;
}
@Override
public Class getElementClass() {
if (elementClass == null)
throw new IllegalStateException("you shall first to call #newInstance(Element)");
return elementClass;
}
@Override
public T newInstance(Element element) {
T entity = newInstance.get();
if (elementClass == null)
elementClass = (Class) entity.getClass();
return entity;
}
@Override
public void io(Element e, T t, IOProcessor p) {
io.io(e, t, p);
}
});
}
@Override
public ,
P extends TypedElementPersister super T>> void anyChildren(Element element, String sequences,
Supplier getter, Consumer setter,
ElementIOFactory factory) {
if (r) {
Element seqE;
if (sequences != null) {
seqE = element.getChild(sequences, element.getNamespace());
if (seqE == null) return;
} else {
seqE = element;
}
List result = new ArrayList<>();
for (Object child : seqE.getChildren()) {
Element childE = (Element) child;
T childT = read(factory, childE);
if (childT != null) {
result.add(childT);
}
}
@SuppressWarnings("unchecked") T[] res = (T[]) Array.newInstance(factory.getBaseElementClass(), result.size());
res = result.toArray(res);
setter.accept(res);
} else {
T[] entities = getter.get();
if (entities == null) return;
Element seqE;
if (sequences != null) {
seqE = initSequenceElement(element, sequences);
} else {
seqE = element;
}
for (T child : entities) {
Element childE = persist(factory, child, element.getNamespace());
if (childE != null) {
installNamespace(childE, element.getNamespace());
seqE.addContent(childE);
}
}
}
}
@Override
public ,
P extends NamespacePersister super T>> void anyChildren(Element element, String sequences,
Supplier getter, Consumer setter,
NamespaceIOFactory factory,
Namespace... defaultNamespace) {
if (r) {
Element seqE;
if (sequences != null) {
seqE = element.getChild(sequences, element.getNamespace());
if (seqE == null) return;
} else {
seqE = element;
}
List result = new ArrayList<>();
for (Object child : seqE.getChildren()) {
Element childE = (Element) child;
T childT = read(factory, childE, seqE.getNamespace(), defaultNamespace);
if (childT != null) {
result.add(childT);
}
}
if (result.size() > 0) {
@SuppressWarnings("unchecked") T[] res;
if (factory.getBaseElementClass() == null) {
res = (T[]) Array.newInstance(NamespaceUriAware.class, result.size());
} else {
res = (T[]) Array.newInstance(factory.getBaseElementClass(), result.size());
}
res = result.toArray(res);
setter.accept(res);
}
} else {
T[] entities = getter.get();
if (entities == null) return;
Element seqE;
if (sequences != null) {
seqE = initSequenceElement(element, sequences);
} else {
seqE = element;
}
for (T child : entities) {
Element childE = persist(factory, child, seqE.getNamespace(), defaultNamespace);
if (childE != null) {
installNamespace(childE, element.getNamespace());
seqE.addContent(childE);
}
}
}
}
@Override
public > void childrenByEnum(Element element, String sequences,
Supplier getterList, Consumer setterList,
Class enumClass, Function getterEnum, BiConsumer setterEnum,
ClassedElementIO io) {
if (r) {
List result = new ArrayList<>();
Element seqE;
if (sequences != null) {
seqE = element.getChild(sequences, element.getNamespace());
if (seqE == null) return;
} else {
seqE = element;
}
for (Object child : seqE.getChildren()) {
Element childE = (Element) child;
E en = stringToEnum(childE.getName(), enumClass);
if (en != null) {
T entity = read(io, childE);
setterEnum.accept(entity, en);
result.add(entity);
}
}
if (result.size() > 0) {
T[] res = (T[]) Array.newInstance(io.getElementClass(), result.size());
res = result.toArray(res);
setterList.accept(res);
}
} else {
T[] entity = getterList.get();
if (entity == null) return;
Element seqE;
if (sequences != null) {
seqE = initSequenceElement(element, sequences);
} else {
seqE = element;
}
for (T child : entity) {
final E en = getterEnum.apply(child);
Element childE = null;
if (en != null) {
childE = persist(new NamedElementIO() {
@Override
public String getElementName() {
return en.name();
}
@Override
public void io(Element e, T t, IOProcessor p) {
io.io(e, t, p);
}
}, child, seqE.getNamespace());
installNamespace(childE, element.getNamespace());
seqE.addContent(childE);
}
}
}
}
@Override
@SuppressWarnings("unchecked")
public > void childrenByEnum(Element element, String sequences,
Supplier getterList, Consumer setterList,
Function getterEnum, BiConsumer setterEnum,
Supplier newInstance, Class enumClass, ElementIO io) {
childrenByEnum(element, sequences, getterList, setterList, enumClass, getterEnum, setterEnum,
new ClassedElementIO() {
private Class elementClass;
@Override
public Class getElementClass() {
if (elementClass == null)
throw new IllegalStateException("you shall first to call #newInstance(Element)");
return elementClass;
}
@Override
public T newInstance(Element element) {
T entity = newInstance.get();
if (elementClass == null)
elementClass = (Class) entity.getClass();
return entity;
}
@Override
public void io(Element e, T t, IOProcessor p) {
io.io(e, t, p);
}
});
}
@Override
public void attribute(Element element, String name, Supplier getter, Consumer setter) {
if (r) {
Attribute attribute = element.getAttribute(name);
if (attribute != null) {
setter.accept(process(attribute.getValue()));
}
} else {
if (getter.get() == null) return;
element.setAttribute(new Attribute(name, getter.get()));
}
}
@Override
public void text(Element element, Supplier getter, Consumer setter) {
if (r) {
String text = element.getText();
if (text != null && !text.isEmpty()) {
setter.accept(process(text));
}
} else {
if (getter.get() == null) return;
element.setText(getter.get());
}
}
@Override
public void childrenText(Element element, String childName, Supplier getter, Consumer setter) {
if (r) {
Element child = element.getChild(childName, element.getNamespace());
if (child == null) return;
String text = child.getText();
if (text != null && !text.isEmpty()) {
setter.accept(process(text));
}
} else {
if (getter.get() == null) return;
Element childElement = element.getChild(childName, element.getNamespace());
if (childElement == null) {
childElement = new Element(childName, element.getNamespace());
childElement.setText(getter.get());
element.addContent(childElement);
} else {
childElement.setText(getter.get());
}
}
}
@Override
public void childAttribute(Element element, String childName, String name, Supplier getter, Consumer setter) {
if (r) {
Element child = element.getChild(childName, element.getNamespace());
if (child == null) return;
Attribute attribute = child.getAttribute(name);
if (attribute != null) {
setter.accept(process(attribute.getValue()));
}
} else {
if (getter.get() == null) return;
Element childElement = element.getChild(childName, element.getNamespace());
if (childElement == null) {
childElement = new Element(childName, element.getNamespace());
childElement.setAttribute(new Attribute(name, getter.get()));
element.addContent(childElement);
} else {
childElement.setAttribute(new Attribute(name, getter.get()));
}
}
}
@Override
public void childAttributeBoolean(Element element, String childName, String name, Supplier getter, Consumer setter) {
if (r) {
Element child = element.getChild(childName, element.getNamespace());
if (child == null) return;
Attribute attribute = child.getAttribute(name);
if (attribute != null) {
setter.accept(Boolean.valueOf(process(attribute.getValue())));
}
} else {
if (getter.get() == null) return;
Element childElement = element.getChild(childName, element.getNamespace());
if (childElement == null) {
childElement = new Element(childName, element.getNamespace());
childElement.setAttribute(new Attribute(name, getter.get().toString()));
element.addContent(childElement);
} else {
childElement.setAttribute(new Attribute(name, getter.get().toString()));
}
}
}
@Override
public void childAttributeInteger(Element element, String childName, String name, Supplier getter, Consumer setter) {
if (r) {
Element child = element.getChild(childName, element.getNamespace());
if (child == null) return;
Attribute attribute = child.getAttribute(name);
if (attribute != null) {
setter.accept(Integer.parseInt(process(attribute.getValue())));
}
} else {
if (getter.get() == null) return;
Element childElement = element.getChild(childName, element.getNamespace());
if (childElement == null) {
childElement = new Element(childName, element.getNamespace());
childElement.setAttribute(new Attribute(name, getter.get().toString()));
element.addContent(childElement);
} else {
childElement.setAttribute(new Attribute(name, getter.get().toString()));
}
}
}
@Override
public > void childAttributeEnum(Element element, String childName, String name, Supplier getter, Consumer setter, Class enumClass) {
if (r) {
Element child = element.getChild(childName, element.getNamespace());
if (child == null) return;
Attribute attribute = child.getAttribute(name);
if (attribute != null) {
setter.accept(stringToEnum(process(attribute.getValue()), enumClass));
}
} else {
if (getter.get() == null) return;
Element childElement = element.getChild(childName, element.getNamespace());
if (childElement == null) {
childElement = new Element(childName, element.getNamespace());
element.addContent(childElement);
}
if (IdAware.class.isAssignableFrom(enumClass))
childElement.setAttribute(new Attribute(name, ((IdAware) getter.get()).getId()));
else
childElement.setAttribute(new Attribute(name, getter.get().name()));
}
}
/**
* Считать атрибуты другой схемы
*
* @param element элемент
* @param namespace схема, атрибуты которой нужно считать
* @param map мапа, в которую считать атрибуты схемы
*/
@Override
public void otherAttributes(Element element, Namespace namespace, Map map) {
if (r) {
for (Object o : element.getAttributes()) {
Attribute attribute = (Attribute) o;
if (attribute.getNamespace().equals(namespace)) {
if (attribute.getValue() instanceof String) {
map.put(attribute.getName(), process(attribute.getValue()));
} else {
map.put(attribute.getName(), attribute.getValue());
}
}
}
} else {
for (Map.Entry entry : map.entrySet()) {
element.setAttribute(new Attribute(entry.getKey(), entry.getValue(), namespace));
}
}
}
@Override
public void childAnyAttributes(Element element, String childName, Supplier>> getter, Consumer>> setter) {
if (r) {
Element child = element.getChild(childName, element.getNamespace());
if (child == null) return;
anyAttributes(child, getter, setter);
} else {
if (getter.get() == null) return;
Element childElement = element.getChild(childName, element.getNamespace());
if (childElement == null) {
childElement = new Element(childName, element.getNamespace());
anyAttributes(childElement, getter, setter);
element.addContent(childElement);
} else {
anyAttributes(childElement, getter, setter);
}
}
}
@Override
public void anyAttributes(Element element, Supplier>> getter,
Consumer>> setter) {
if (r) {
N2oNamespace elementNamespace = new N2oNamespace(element.getNamespace());
Map> extensions = new HashMap<>();
for (Object o : element.getAttributes()) {
Attribute attribute = (Attribute) o;
if (elementNamespace.getUri().equals(attribute.getNamespaceURI()) || attribute.getNamespaceURI().isEmpty()) {
continue;
} else {
N2oNamespace namespace = new N2oNamespace(attribute.getNamespace());
extensions.putIfAbsent(namespace, new HashMap<>());
extensions.get(namespace).put(attribute.getName(), process(attribute.getValue()));
}
}
setter.accept(extensions);
} else {
Map> extensions = getter.get();
if (extensions == null)
return;
for (Map.Entry> map : extensions.entrySet()) {
for (Map.Entry entry : map.getValue().entrySet()) {
element.setAttribute(new Attribute(entry.getKey(), entry.getValue(), Namespace.getNamespace(map.getKey().getPrefix(), map.getKey().getUri())));
}
}
}
}
@Override
public void attributeBoolean(Element element, String name, Supplier getter, Consumer setter) {
if (r) {
Attribute attribute = element.getAttribute(name);
if (attribute != null) {
setter.accept(Boolean.valueOf(process(attribute.getValue())));
}
} else {
if (getter.get() == null) return;
element.setAttribute(new Attribute(name, getter.get().toString()));
}
}
@Override
public void attributeInteger(Element element, String name, Supplier getter, Consumer setter) {
if (r) {
Attribute attribute = element.getAttribute(name);
if (attribute != null) {
setter.accept(Integer.valueOf(process(attribute.getValue())));
}
} else {
if (getter.get() == null) return;
element.setAttribute(new Attribute(name, getter.get().toString()));
}
}
@Override
public void attributeArray(Element element, String name, String separator, Supplier getter, Consumer setter) {
if (r) {
Attribute attribute = element.getAttribute(name);
if (attribute != null) {
String value = process(attribute.getValue());
setter.accept(value.trim().split("\\s*" + separator + "\\s*"));
}
} else {
if (getter.get() == null) return;
StringJoiner str = new StringJoiner(",");
for (String s : getter.get())
str.add(s);
element.setAttribute(new Attribute(name, str.toString()));
}
}
@Override
public > void attributeEnum(Element element, String name, Supplier getter, Consumer setter, Class enumClass) {
if (r) {
Attribute attribute = element.getAttribute(name);
if (attribute != null) {
setter.accept(stringToEnum(process(attribute.getValue()), enumClass));
}
} else {
if (getter.get() == null) return;
if (IdAware.class.isAssignableFrom(enumClass)) {
element.setAttribute(new Attribute(name, ((IdAware) getter.get()).getId()));
} else {
element.setAttribute(new Attribute(name, getter.get().name()));
}
}
}
@Override
public void element(Element element, String name, Supplier getter, Consumer setter) {
if (r) {
Element child = element.getChild(name, element.getNamespace());
if (child != null && child.getValue() != null && !child.getValue().isEmpty()) {
setter.accept(process(child.getValue()));
}
} else {
if (getter.get() == null || getter.get().isEmpty()) return;
Element childElement = element.getChild(name, element.getNamespace());
if (childElement == null) {
childElement = new Element(name, element.getNamespace());
childElement.setText(getter.get());
element.addContent(childElement);
} else {
childElement.setText(getter.get());
}
}
}
@Override
public void hasElement(Element element, String name, Supplier getter, Consumer setter) {
if (r) {
Element child = element.getChild(name, element.getNamespace());
setter.accept(child != null);
} else {
if (getter.get() == null || !getter.get()) return;
if (element.getChild(name, element.getNamespace()) == null) {
Element childElement = new Element(name, element.getNamespace());
element.addContent(childElement);
}
}
}
@Override
public , P extends TypedElementPersister super T>> ElementIOFactory oneOf(Class baseElementClass) {
return new ElementIOFactoryByMap<>(baseElementClass);
}
@Override
public , P extends NamespacePersister super T>> NamespaceIOFactory anyOf(Class baseElementClass) {
return new NamespaceIOFactoryByMap<>(baseElementClass, readerFactory, persisterFactory);
}
@Override
public , P extends NamespacePersister super T>> NamespaceIOFactory anyOf() {
return new NamespaceIOFactoryByMap<>(null, readerFactory, persisterFactory);
}
/**
* Установить схему всем дочерним элементам
*
* @param element элемент
* @param namespace схема
*/
private void installNamespace(Element element, Namespace namespace) {
if (element.getNamespace().equals(Namespace.NO_NAMESPACE)) {
element.setNamespace(namespace);
for (Object o : element.getChildren()) {
Element child = (Element) o;
installNamespace(child, namespace);
}
}
}
/**
* Установить схему всем дочерним элементам
*
* @param element элемент
* @param namespace схема
*/
private void installNamespace(Element element, Namespace namespace, Namespace oldNamespace) {
if (element.getNamespace().equals(oldNamespace)) {
element.setNamespace(namespace);
for (Object o : element.getChildren()) {
Element child = (Element) o;
installNamespace(child, namespace, oldNamespace);
}
}
}
/**
* Чтение настроек и локализации
*
* @param text текст с плейсхолдерами ${prop}
* @return текст без плейсхолдеров, если они разрешились
*/
private String process(String text) {
if (text == null) {
return null;
}
String resolved = StringUtils.resolveProperties(text, MetadataParamHolder.getParams());
resolved = systemProperties == null ? resolved : StringUtils.resolveProperties(resolved, systemProperties::getProperty);
resolved = messageSourceAccessor == null ? resolved : StringUtils.resolveProperties(resolved, (msg) -> messageSourceAccessor.getMessage(msg, msg));
if (failFast && StringUtils.hasProperty(resolved))
throw new N2oException("Cannot resolve property in '" + text + "'");
return resolved;
}
/**
* Конвертирует строку в enum
*
* @param value строка
* @param enumClass класс enum
* @param
* @return
*/
private static > T stringToEnum(String value, Class enumClass) {
if (value == null) return null;
T res = null;
boolean idAware = IdAware.class.isAssignableFrom(enumClass);
if (idAware) {
for (Enum enumValue : enumClass.getEnumConstants()) {
IdAware idEnum = (IdAware) enumValue;
if (idEnum.getId().equalsIgnoreCase(value)) {
res = (T) enumValue;
}
}
} else {
for (Enum enumValue : enumClass.getEnumConstants()) {
if (enumValue.name().equalsIgnoreCase(value)) {
res = (T) enumValue;
}
}
}
return res;
}
private Element persist(NamedElementIO io, T entity, Namespace namespace) {
Element element = new Element(io.getElementName(), namespace);
io.io(element, entity, this);
return element;
}
private T read(ClassedElementIO io, Element element) {
T entity = io.newInstance(element);
io.io(element, entity, this);
return entity;
}
private ,
P extends TypedElementPersister super T>> T read(ElementIOFactory factory, Element element) {
R reader = factory.produce(element);
if (reader != null) {
if (reader instanceof IOProcessorAware)
((IOProcessorAware) reader).setIOProcessor(this);
return reader.read(element);
} else
return null;
}
private ,
P extends TypedElementPersister super T>> Element persist(ElementIOFactory factory, T entity, Namespace namespace) {
P persister = factory.produce(entity);
if (persister != null) {
if (persister instanceof IOProcessorAware)
((IOProcessorAware) persister).setIOProcessor(this);
return persister.persist(entity, namespace);
} else
return null;
}
private ,
P extends NamespacePersister super T>> T read(NamespaceIOFactory factory, Element element,
Namespace parentNamespace, Namespace... defaultNamespaces) {
R reader;
if (defaultNamespaces != null && defaultNamespaces.length > 0 && defaultNamespaces[0] != null && (hasText(getParentNameSpacePrefix(element)) || parentNamespace.getURI().equals(element.getNamespaceURI()))) {
reader = factory.produce(element, parentNamespace, ArrayUtils.add(defaultNamespaces, element.getNamespace()));
} else {
reader = factory.produce(element, parentNamespace, null);
}
if (reader != null) {
if (reader instanceof IOProcessorAware)
((IOProcessorAware) reader).setIOProcessor(this);
T model = reader.read(element);
model.setNamespaceUri(element.getNamespaceURI());
model.setNamespacePrefix(element.getNamespacePrefix());
return model;
} else
return null;
}
private ,
P extends NamespacePersister super T>> Element persist(NamespaceIOFactory factory, T entity,
Namespace parentNamespace, Namespace... defaultNamespaces) {
P persister;
if (defaultNamespaces != null && defaultNamespaces.length > 0 && defaultNamespaces[0] != null
&& (isEmpty(entity.getNamespacePrefix()) || entity.getNamespaceUri().equals(parentNamespace.getURI())))
persister = factory.produce((Class) entity.getClass(), ArrayUtils.add(defaultNamespaces, entity.getNamespace()));
else
persister = factory.produce(entity);
if (persister != null) {
if (persister instanceof IOProcessorAware)
((IOProcessorAware) persister).setIOProcessor(this);
Element element = persister.persist(entity, parentNamespace);
installNamespace(element, entity.getNamespace(), element.getNamespace());
return element;
} else
return null;
}
private String getParentNameSpacePrefix(Element element) {
if (isNull(element))
return null;
return nonNull(element.getParentElement()) ? element.getParentElement().getNamespacePrefix() : null;
}
private Element initSequenceElement(Element parent, String seqName) {
Element seqE = parent.getChild(seqName, parent.getNamespace());
if (seqE == null) {
seqE = new Element(seqName, parent.getNamespace());
parent.addContent(seqE);
}
return seqE;
}
public void setMessageSourceAccessor(MessageSourceAccessor messageSourceAccessor) {
this.messageSourceAccessor = messageSourceAccessor;
}
public void setSystemProperties(PropertyResolver systemProperties) {
this.systemProperties = systemProperties;
}
public void setFailFast(boolean failFast) {
this.failFast = failFast;
}
}