/** * ============================================================================= * * ORCID (R) Open Source * http://orcid.org * * Copyright (c) 2012-2014 ORCID, Inc. * Licensed under an MIT-Style License (MIT) * http://orcid.org/open-source-license * * This copyright and license information (including a link to the full license) * shall be included in its entirety in all copies or substantial portion of * the software. * * ============================================================================= */ package org.orcid.core.version.impl; import java.util.concurrent.ConcurrentHashMap; import org.apache.commons.lang3.tuple.ImmutablePair; import org.apache.commons.lang3.tuple.Pair; import org.orcid.core.version.V2VersionObjectFactory; /** * * @author Will Simpson * */ public class V2VersionObjectFactoryImpl implements V2VersionObjectFactory { private final ConcurrentHashMap<Pair<Class<?>, String>, Class<?>> classMap = new ConcurrentHashMap<>(); @Override public Object createEquivalentInstance(Object originalObject, String requiredVersion) { Class<?> originalClass = originalObject.getClass(); Pair<Class<?>, String> key = new ImmutablePair<>(originalClass, requiredVersion); Class<?> requiredClass = classMap.get(key); if (requiredClass == null) { requiredClass = createClass(originalClass, requiredVersion); classMap.put(key, requiredClass); } return createInstance(requiredClass); } private Class<?> createClass(Class<?> originalClass, String requiredVersion) { try { return Class.forName(calculateClassFullName(originalClass, requiredVersion)); } catch (ClassNotFoundException e) { throw new RuntimeException("Unable to find equivalent class for " + originalClass + " in version " + requiredVersion, e); } } private String calculateClassFullName(Class<?> originalClass, String requiredVersion) { String requiredMinorVersion = requiredVersion.equals("2.0") ? "v2" : requiredVersion.substring(requiredVersion.lastIndexOf('_') + 1); String originalPackageName = originalClass.getPackage().getName(); String packageNameBase = originalPackageName.substring(0, originalPackageName.lastIndexOf('_') + 1); String originalClassName = originalClass.getSimpleName(); String requiredClassFullName = packageNameBase + requiredMinorVersion + '.' + originalClassName; return requiredClassFullName; } private Object createInstance(Class<?> requiredClass) { try { return requiredClass.newInstance(); } catch (InstantiationException e) { throw new RuntimeException("Problem instantiating class " + requiredClass.getName(), e); } catch (IllegalAccessException e) { throw new RuntimeException("Problem accessing class " + requiredClass.getName(), e); } } }