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.
io.atlasmap.java.core.JavaFieldReader Maven / Gradle / Ivy
package io.atlasmap.java.core;
import java.lang.reflect.Array;
import java.lang.reflect.Method;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.List;
import java.util.Map;
import org.slf4j.LoggerFactory;
import io.atlasmap.api.AtlasException;
import io.atlasmap.core.AtlasPath;
import io.atlasmap.core.AtlasPath.SegmentContext;
import io.atlasmap.core.AtlasUtil;
import io.atlasmap.java.v2.JavaEnumField;
import io.atlasmap.java.v2.JavaField;
import io.atlasmap.spi.AtlasConversionService;
import io.atlasmap.spi.AtlasFieldReader;
import io.atlasmap.spi.AtlasInternalSession;
import io.atlasmap.v2.AtlasModelFactory;
import io.atlasmap.v2.AuditStatus;
import io.atlasmap.v2.CollectionType;
import io.atlasmap.v2.Field;
import io.atlasmap.v2.FieldGroup;
public class JavaFieldReader implements AtlasFieldReader {
private static final org.slf4j.Logger LOG = LoggerFactory.getLogger(JavaFieldReader.class);
private AtlasConversionService conversionService;
private Object sourceDocument;
@Override
public Field read(AtlasInternalSession session) throws AtlasException {
try {
Field sourceField = session.head().getSourceField();
Method getter = null;
if (sourceField.getFieldType() == null
&& (sourceField instanceof JavaField || sourceField instanceof JavaEnumField)) {
getter = resolveGetMethod(session, sourceDocument, sourceField);
if (getter == null) {
AtlasUtil.addAudit(session, sourceField.getDocId(), String.format(
"Unable to auto-detect sourceField type path=%s docId=%s",
sourceField.getPath(), sourceField.getDocId()),
sourceField.getPath(), AuditStatus.WARN, null);
return sourceField;
}
Class> returnType = getter.getReturnType();
sourceField.setFieldType(conversionService.fieldTypeFromClass(returnType));
if (LOG.isTraceEnabled()) {
LOG.trace("Auto-detected sourceField type p=" + sourceField.getPath() + " t="
+ sourceField.getFieldType());
}
}
populateSourceFieldValue(session, sourceField, sourceDocument, getter);
if (LOG.isDebugEnabled()) {
LOG.debug("Processed input field sPath=" + sourceField.getPath() + " sV=" + sourceField.getValue()
+ " sT=" + sourceField.getFieldType() + " docId: " + sourceField.getDocId());
}
return session.head().getSourceField();
} catch (Exception e) {
throw new AtlasException(e);
}
}
private void populateSourceFieldValue(AtlasInternalSession session, Field field, Object source, Method m) throws Exception {
Method getter = m;
AtlasPath atlasPath = new AtlasPath(field.getPath());
FieldGroup fieldGroup = null;
if (atlasPath.hasCollection() && !atlasPath.isIndexedCollection()) {
fieldGroup = AtlasModelFactory.createFieldGroupFrom(field);
session.head().setSourceField(fieldGroup);
}
List parents = Arrays.asList(source);
if (atlasPath.isRoot()) {
if (atlasPath.getLastSegment().getCollectionType() == CollectionType.NONE) {
processField(fieldGroup, field, source);
} else {
if (atlasPath.getLastSegment().getCollectionIndex() != null) {
processField(fieldGroup, field, extractFromCollection(session, source, atlasPath));
} else {
if (source instanceof Collection) {
for (Object item : ((Collection>)source).toArray()) {
processField(fieldGroup, field, item);
}
} else if (source.getClass().isArray()) {
for (int i=0; i)child).toArray()) {
processField(fieldGroup, field, item);
}
} else if (child.getClass().isArray()) {
for (int i=0; i parents = ClassHelper.getParentObjectsForPath(session, sourceObject, atlasPath);
parentObject = parents != null && parents.size() > 0 ? parents.get(0) : null;
}
if (parentObject == null) {
return null;
}
List> classTree = resolveMappableClasses(parentObject.getClass());
for (Class> clazz : classTree) {
try {
if (field instanceof JavaField && ((JavaField) field).getGetMethod() != null) {
getter = clazz.getMethod(((JavaField) field).getGetMethod());
getter.setAccessible(true);
return getter;
}
} catch (NoSuchMethodException e) {
// no getter method specified in mapping file
}
for (String m : Arrays.asList("get", "is")) {
String getterMethod = m + capitalizeFirstLetter(atlasPath.getLastSegment().getName());
try {
getter = clazz.getMethod(getterMethod);
getter.setAccessible(true);
return getter;
} catch (NoSuchMethodException e) {
// method does not exist
}
}
}
return null;
}
private Object getValueFromMemberField(AtlasInternalSession session, Object source, String fieldName) throws IllegalArgumentException, IllegalAccessException {
java.lang.reflect.Field reflectField = lookupJavaField(source, fieldName);
if (reflectField != null) {
reflectField.setAccessible(true);
return reflectField.get(source);
}
Field sourceField = session.head().getSourceField();
AtlasUtil.addAudit(session, sourceField.getDocId(), String.format(
"Field '%s' not found on object '%s'", fieldName, source),
sourceField.getPath(), AuditStatus.ERROR, null);
return null;
}
private List> resolveMappableClasses(Class> className) {
List> classTree = new ArrayList<>();
classTree.add(className);
Class> superClazz = className.getSuperclass();
while (superClazz != null) {
if (JdkPackages.contains(superClazz.getPackage().getName())) {
superClazz = null;
} else {
classTree.add(superClazz);
superClazz = superClazz.getSuperclass();
}
}
return classTree;
}
private java.lang.reflect.Field lookupJavaField(Object source, String fieldName) {
Class> targetClazz = source != null ? source.getClass() : null;
while (targetClazz != null && targetClazz != Object.class) {
try {
return targetClazz.getDeclaredField(fieldName);
} catch (Exception e) {
e.getMessage(); // ignore
targetClazz = targetClazz.getSuperclass();
}
}
return null;
}
private String capitalizeFirstLetter(String sentence) {
if (StringUtil.isEmpty(sentence)) {
return sentence;
}
if (sentence.length() == 1) {
return String.valueOf(sentence.charAt(0)).toUpperCase();
}
return String.valueOf(sentence.charAt(0)).toUpperCase() + sentence.substring(1);
}
private Object extractFromCollection(AtlasInternalSession session, Object source, AtlasPath atlasPath) {
if (source == null) {
return null;
}
SegmentContext lastSegment = atlasPath.getLastSegment();
CollectionType collectionType = lastSegment.getCollectionType();
Integer index = lastSegment.getCollectionIndex();
if (collectionType == CollectionType.NONE || index == null) {
return source;
}
if (collectionType == CollectionType.ARRAY) {
return Array.get(source, index);
} else if (collectionType == CollectionType.LIST) {
return Collection.class.cast(source).toArray()[index];
} else if (collectionType == CollectionType.MAP) {
// TODO support map key
String key = index.toString();
return Map.class.cast(source).get(key);
} else {
Field sourceField = session.head().getSourceField();
AtlasUtil.addAudit(session, sourceField.getDocId(), String.format(
"Ignoring unknown collection type in path '%s'", sourceField.getPath()),
sourceField.getPath(), AuditStatus.WARN, null);
return source;
}
}
public void setDocument(Object sourceDocument) {
this.sourceDocument = sourceDocument;
}
public void setConversionService(AtlasConversionService conversionService) {
this.conversionService = conversionService;
}
}