blob: ce123e1c925126a8fdc47db98721e4cc1533395e [file] [log] [blame]
/*
* Copyright 2016-present Open Networking Laboratory
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.onosproject.yms.app.ysr;
import org.onosproject.yangutils.datamodel.RpcNotificationContainer;
import org.onosproject.yangutils.datamodel.YangInclude;
import org.onosproject.yangutils.datamodel.YangModule;
import org.onosproject.yangutils.datamodel.YangNode;
import org.onosproject.yangutils.datamodel.YangSchemaNode;
import org.onosproject.yangutils.datamodel.YangSubModule;
import org.onosproject.yangutils.datamodel.exceptions.DataModelException;
import org.onosproject.yms.ysr.YangModuleIdentifier;
import org.onosproject.yms.ysr.YangModuleInformation;
import org.onosproject.yms.ysr.YangModuleLibrary;
import org.osgi.framework.BundleContext;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashSet;
import java.util.Iterator;
import java.util.List;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentMap;
import java.util.regex.Pattern;
import static org.apache.commons.io.FileUtils.deleteDirectory;
import static org.onosproject.yangutils.datamodel.utils.DataModelUtils.parseJarFile;
import static org.onosproject.yangutils.utils.UtilConstants.DEFAULT;
import static org.onosproject.yangutils.utils.UtilConstants.EMPTY_STRING;
import static org.onosproject.yangutils.utils.UtilConstants.EVENT_STRING;
import static org.onosproject.yangutils.utils.UtilConstants.OP_PARAM;
import static org.onosproject.yangutils.utils.UtilConstants.PERIOD;
import static org.onosproject.yangutils.utils.io.impl.YangIoUtils.getCapitalCase;
import static org.osgi.framework.FrameworkUtil.getBundle;
/**
* Representation of default YANG schema registry. Yang schema registry
* provides interface to an application to register its YANG schema
* with YMS. It provides YANG schema nodes to YDT, YNB and YSB.
*/
public class DefaultYangSchemaRegistry
implements YangSchemaRegistry {
private static final String SYSTEM = File.separator + "system" +
File.separator;
private static final String MAVEN = "mvn:";
private static final String HYPHEN = "-";
private static final String DELIMITER = ".";
private static final String SERVICE = "Service";
private static final String JAR = ".jar";
private static final String USER_DIRECTORY = "user.dir";
private static final String SLASH = File.separator;
private static final String AT = "@";
private static final String DATE_FORMAT = "yyyy-mm-dd";
private static final Logger log =
LoggerFactory.getLogger(DefaultYangSchemaRegistry.class);
private final ConcurrentMap<String, YsrAppContext> appObjectStore;
private final ConcurrentMap<String, YsrAppContext> yangSchemaStore;
private final ConcurrentMap<String, YsrAppContext>
yangSchemaStoreForRootInterface;
private final ConcurrentMap<String, YsrAppContext>
yangSchemaStoreForRootOpParam;
private final ConcurrentMap<String, YsrAppContext>
yangRootSchemaStoreForNotification;
private final ConcurrentMap<String, Class<?>> registerClassStore;
private final ConcurrentMap<YangModuleIdentifier, String> yangFileStore;
private final YangModuleLibrary library;
private YsrAppContext ysrAppContext;
private YsrAppContext ysrContextForSchemaStore;
private YsrAppContext ysrContextForAppStore;
private ClassLoader classLoader;
/**
* Creates an instance of default YANG schema registry.
*
* @param moduleId module set id of YSR module library
*/
public DefaultYangSchemaRegistry(String moduleId) {
appObjectStore = new ConcurrentHashMap<>();
yangSchemaStore = new ConcurrentHashMap<>();
yangSchemaStoreForRootInterface = new ConcurrentHashMap<>();
yangSchemaStoreForRootOpParam = new ConcurrentHashMap<>();
yangRootSchemaStoreForNotification = new ConcurrentHashMap<>();
registerClassStore = new ConcurrentHashMap<>();
yangFileStore = new ConcurrentHashMap<>();
library = new DefaultYangModuleLibrary(moduleId);
}
@Override
public void registerApplication(Object appObject, Class<?> serviceClass) {
BundleContext bundleContext = getBundle(serviceClass)
.getBundleContext();
String jarPath = getJarPathFromBundleLocation(
bundleContext.getBundle().getLocation(),
bundleContext.getProperty(USER_DIRECTORY));
processRegistration(serviceClass, appObject, jarPath);
}
/**
* Process application registration.
*
* @param serviceClass service class
* @param appObject application object
* @param jarPath jar path
*/
void processRegistration(Class<?> serviceClass, Object appObject,
String jarPath) {
// set class loader for service class.
setClassLoader(serviceClass.getClassLoader());
//Check if service should be registered?
if (appObject != null) {
verifyApplicationRegistration(appObject, serviceClass);
}
//Add app class to registered service store.
if (!registerClassStore.containsKey(serviceClass.getName())) {
updateServiceClass(serviceClass);
}
// process storing operations.
if (!verifyIfApplicationAlreadyRegistered(serviceClass)) {
List<YangNode> curNodes =
processJarParsingOperations(jarPath);
if (curNodes != null) {
for (YangNode schemaNode : curNodes) {
//Process application context for registrations.
processApplicationContext(schemaNode);
//Update YANG file store.
updateYangFileStore(schemaNode, jarPath);
//Process module library operation for current node list.
processModuleLibrary(schemaNode);
}
//Set jar path for app context.
ysrAppContext.jarPath(jarPath);
ysrContextForSchemaStore.jarPath(jarPath);
ysrContextForAppStore.jarPath(jarPath);
}
}
//Verifies if object is updated for app store.
updateApplicationObject(appObject, serviceClass);
}
/**
* Verifies if service class should be registered or not.
*
* @param appObject application object
* @param appClass application class
*/
private void verifyApplicationRegistration(Object appObject,
Class<?> appClass) {
Class<?> managerClass = appObject.getClass();
Class<?>[] services = managerClass.getInterfaces();
List<Class<?>> classes = new ArrayList<>();
Collections.addAll(classes, services);
if (!classes.contains(appClass)) {
throw new RuntimeException("service class " + appClass.getName() +
"is not being implemented by " +
managerClass.getName());
}
}
/**
* Verifies if application is already registered with YMS.
*
* @param appClass application class
* @return true if application already registered
*/
private boolean verifyIfApplicationAlreadyRegistered(Class<?> appClass) {
String simpleName = appClass.getSimpleName();
String appName = appClass.getName();
if (!appObjectStore.containsKey(appName)) {
if (simpleName.contains(OP_PARAM)) {
return yangSchemaStoreForRootOpParam
.containsKey(appName);
} else {
return yangSchemaStoreForRootInterface
.containsKey(appName);
}
}
return true;
}
/**
* Verifies if service is being implemented by some new object.
*
* @param appObject application's object
* @param appClass application's class
*/
private void updateApplicationObject(Object appObject, Class<?> appClass) {
YsrAppContext appContext =
appObjectStore.get(appClass.getName());
if (appContext != null) {
YangSchemaNode schemaNode = appContext.curNode();
String name = getInterfaceClassName(schemaNode);
if (appContext.appObject() == null) {
//update in application store.
appContext.appObject(appObject);
//Update app object for schema store for root interface.
appContext = yangSchemaStoreForRootInterface.get(name);
if (appContext != null) {
appContext.appObject(appObject);
}
// Update app object for schema store for root op param
appContext = yangSchemaStoreForRootOpParam.get(name + OP_PARAM);
if (appContext != null) {
appContext.appObject(appObject);
}
}
}
}
@Override
public void unRegisterApplication(Object managerObject,
Class<?> serviceClass) {
YangSchemaNode curNode = null;
String serviceName = serviceClass.getName();
//Check if service should be unregistered?
if (managerObject != null) {
verifyApplicationRegistration(managerObject, serviceClass);
}
//Remove registered class from store.
registerClassStore.remove(serviceName);
//check if service is in app store.
if (appObjectStore.containsKey(serviceName)) {
curNode = retrieveNodeForUnregister(serviceName, appObjectStore,
managerObject);
} else if (yangSchemaStoreForRootInterface.containsKey(serviceName)) {
//check if service is in interface store.
curNode = retrieveNodeForUnregister(serviceName,
yangSchemaStoreForRootInterface,
managerObject);
} else if (yangSchemaStoreForRootOpParam.containsKey(serviceName)) {
//check if service is in op param store.
curNode = retrieveNodeForUnregister(serviceName,
yangSchemaStoreForRootOpParam,
managerObject);
}
if (curNode != null) {
String javaName = getInterfaceClassName(curNode);
removeFromYangSchemaStore(curNode);
removeFromYangNotificationStore(curNode);
removeFromAppSchemaStore(serviceName);
removeFromYangSchemaNodeForRootInterface(javaName);
removeFromYangSchemaNodeForRootOpParam(javaName);
removeYangFileInfoFromStore(curNode);
log.info(" service {} is unregistered.",
serviceClass.getSimpleName());
} else {
throw new RuntimeException(serviceClass.getSimpleName() +
" service was not registered.");
}
}
@Override
public Object getRegisteredApplication(YangSchemaNode schemaNode) {
if (schemaNode != null) {
String name = getInterfaceClassName(schemaNode);
if (yangSchemaStoreForRootInterface.containsKey(name)) {
return yangSchemaStoreForRootInterface.get(name)
.appObject();
}
log.error("{} not found.", name);
}
return null;
}
@Override
public YangSchemaNode getYangSchemaNodeUsingSchemaName(String schemaName) {
return getSchemaNodeUsingSchemaNameWithRev(schemaName);
}
@Override
public YangSchemaNode getYangSchemaNodeUsingAppName(String appName) {
YsrAppContext appContext = appObjectStore.get(appName);
if (appContext != null) {
return appContext.curNode();
}
log.error("{} not found.", appName);
return null;
}
@Override
public YangSchemaNode
getYangSchemaNodeUsingGeneratedRootNodeInterfaceFileName(String name) {
YsrAppContext appContext = yangSchemaStoreForRootInterface.get(name);
if (appContext != null) {
return appContext.curNode();
}
log.error("{} not found.", name);
return null;
}
@Override
public YangSchemaNode getYangSchemaNodeUsingGeneratedRootNodeOpPramFileName(
String name) {
YsrAppContext appContext = yangSchemaStoreForRootOpParam.get(name);
if (appContext != null) {
return appContext.curNode();
}
log.error("{} not found.", name);
return null;
}
@Override
public YangSchemaNode getRootYangSchemaNodeForNotification(String name) {
YsrAppContext appContext = yangRootSchemaStoreForNotification.get(name);
if (appContext != null) {
return appContext.curNode();
}
log.error("{} not found.", name);
return null;
}
@Override
public Class<?> getRegisteredClass(YangSchemaNode schemaNode,
String appName) {
String interfaceName = getInterfaceClassName(schemaNode);
String serviceName = getServiceName(schemaNode);
String defaultClass;
if (schemaNode instanceof RpcNotificationContainer) {
defaultClass = getOpParamClassName(schemaNode);
} else {
defaultClass = getDefaultClassName(schemaNode);
}
//If application class is registered.
if (registerClassStore.containsKey(appName)) {
return registerClassStore.get(appName);
} else if (registerClassStore.containsKey(interfaceName)) {
//If interface class is registered.
return registerClassStore.get(interfaceName);
} else if (registerClassStore.containsKey(serviceName)) {
//If service class is registered.
return registerClassStore.get(serviceName);
} else if (registerClassStore.containsKey(defaultClass)) {
//If default class is registered.
return registerClassStore.get(defaultClass);
}
return null;
}
/**
* Returns YANG file path for module identifier.
*
* @param moduleIdentifier module identifier
* @return YANG file path for module identifier
*/
public String getYangFile(YangModuleIdentifier moduleIdentifier) {
if (yangFileStore.containsKey(moduleIdentifier)) {
return yangFileStore.get(moduleIdentifier);
}
log.error("YANG files for corresponding module identifier {} not " +
"found", moduleIdentifier);
return null;
}
/**
* Updates service class store.
*
* @param serviceClass service class
*/
void updateServiceClass(Class<?> serviceClass) {
registerClassStore.put(serviceClass.getName(), serviceClass);
}
/**
* Updates application object store.
*
* @param appName application name
*/
private void updateAppObjectStore(String appName) {
if (verifyClassExistence(appName)) {
appObjectStore.put(appName, ysrContextForAppStore);
}
}
/**
* Updates YANG schema object store.
*
* @param schemaNode application's schema node
*/
private void updateYangSchemaStore(YangSchemaNode schemaNode) {
addSchemaNodeUsingSchemaNameWithRev(schemaNode);
}
/**
* Updates YANG schema notification object store.
*
* @param name application's notification name
*/
private void updateYangNotificationStore(String name) {
if (verifyClassExistence(name)) {
yangRootSchemaStoreForNotification.put(name, ysrAppContext);
}
}
/**
* Updates YANG schema object store for root interface file name.
*
* @param name name of generated interface file for root
* node
*/
private void updateYangSchemaForRootInterfaceFileNameStore(String name) {
if (verifyClassExistence(name)) {
yangSchemaStoreForRootInterface.put(name, ysrAppContext);
}
}
/**
* Updates YANG schema object store for root op param file name.
*
* @param name name of generated op param file for root node
*/
private void updateYangSchemaForRootOpParamFileNameStore(String name) {
if (verifyClassExistence(name)) {
yangSchemaStoreForRootOpParam.put(name, ysrAppContext);
}
}
/**
* Updates yang file store for YANG node.
*
* @param node YANG node
* @param jarPath jar file path
*/
private void updateYangFileStore(YangNode node, String jarPath) {
//FIXME: fix when yang tools support for file name.
//yangFileStore.put(getModuleIdentifier(node),
// getYangFilePath(jarPath, node.getFileName()));
}
/**
* Returns yang file path.
*
* @param jarPath jar path
* @param metaDataFileName name of yang file from metadata
* @return yang file path
*/
private String getYangFilePath(String jarPath, String metaDataFileName) {
String[] metaData = metaDataFileName.split(SLASH);
return jarPath + SLASH + metaData[metaData.length - 1];
}
/**
* Process jar file for fetching YANG nodes.
*
* @param path jar file path
* @return YANG schema nodes
*/
private List<YangNode> processJarParsingOperations(String path) {
//Deserialize data model and get the YANG node set.
try {
return parseJarFile(path + JAR, path);
} catch (IOException e) {
log.error(" failed to parse the jar file in path {} : {} ", path,
e.getMessage());
}
return null;
}
/**
* Process an application an updates the maps for YANG schema registry.
*
* @param appNode application YANG schema nodes
*/
void processApplicationContext(YangSchemaNode appNode) {
String appName = getInterfaceClassName(appNode);
//Create a new instance of ysr app context for each node.
ysrAppContext = new YsrAppContext();
ysrContextForSchemaStore = new YsrAppContext();
ysrContextForAppStore = new YsrAppContext();
//add cur node to app context.
ysrAppContext.curNode(appNode);
ysrContextForAppStore.curNode(appNode);
//Updates maps wih schema nodes.
updateAppObjectStore(getServiceName(appNode));
// Updates schema store.
updateYangSchemaStore(appNode);
// update interface store.
updateYangSchemaForRootInterfaceFileNameStore(appName);
//update op param store.
updateYangSchemaForRootOpParamFileNameStore(getOpParamClassName(appNode));
//Checks if notification is present then update notification store map.
String eventSubject = null;
try {
if (appNode.isNotificationPresent()) {
eventSubject = getEventClassName(appNode);
}
} catch (DataModelException e) {
log.error("failed to search notification from schema map : {}",
e.getLocalizedMessage());
}
if (eventSubject != null) {
updateYangNotificationStore(eventSubject);
}
log.info("successfully registered this application {}{}", appName,
SERVICE);
}
/**
* Returns jar path from bundle mvnLocationPath.
*
* @param mvnLocationPath mvnLocationPath of bundle
* @return path of jar
*/
private String getJarPathFromBundleLocation(String mvnLocationPath,
String currentDirectory) {
String path = currentDirectory + SYSTEM;
String[] strArray = mvnLocationPath.split(MAVEN);
String[] split = strArray[1].split(File.separator);
String[] groupId = split[0].split(Pattern.quote(DELIMITER));
return path + groupId[0] + SLASH + groupId[1] + SLASH + split[1] +
SLASH + split[2] + SLASH + split[1] + HYPHEN + split[2];
}
/**
* Returns de-serializes YANG data-model nodes.
*
* @param serializedFileInfo serialized File Info
* @return de-serializes YANG data-model nodes
*/
Set<YangSchemaNode> deSerializeDataModel(String serializedFileInfo) {
Set<YangSchemaNode> nodes = new HashSet<>();
Object readValue;
try {
FileInputStream fileInputStream =
new FileInputStream(serializedFileInfo);
ObjectInputStream objectInputStream =
new ObjectInputStream(fileInputStream);
readValue = objectInputStream.readObject();
if (readValue instanceof Set<?>) {
for (Object obj : (Set<?>) readValue) {
if (obj instanceof YangSchemaNode) {
nodes.add((YangSchemaNode) obj);
} else {
throw new RuntimeException(
"deserialize object is not an instance of " +
"YANG schema node" + obj);
}
}
} else {
throw new RuntimeException(
"deserialize object is not an instance of set of" +
"YANG schema node" + readValue);
}
objectInputStream.close();
fileInputStream.close();
} catch (IOException | ClassNotFoundException e) {
log.error(" {} not found.: {}", serializedFileInfo,
e.getLocalizedMessage());
}
return nodes;
}
/**
* Returns ysr app context.
*
* @return ysr app context
*/
YsrAppContext ysrAppContext() {
return ysrAppContext;
}
/**
* Returns schema node based on the revision.
*
* @param name name of the schema node
* @return schema node based on the revision
*/
private YangSchemaNode getSchemaNodeUsingSchemaNameWithRev(String name) {
YsrAppContext appContext;
YangSchemaNode schemaNode;
if (name.contains(AT)) {
String[] revArray = name.split(AT);
appContext = yangSchemaStore.get(revArray[0]);
schemaNode = appContext.getSchemaNodeForRevisionStore(name);
if (schemaNode != null) {
return schemaNode;
}
return appContext.curNode();
}
if (yangSchemaStore.containsKey(name)) {
appContext = yangSchemaStore.get(name);
if (appContext != null) {
Iterator<YangSchemaNode> iterator = appContext
.getYangSchemaNodeForRevisionStore().values()
.iterator();
if (iterator.hasNext()) {
return appContext.getYangSchemaNodeForRevisionStore()
.values().iterator().next();
} else {
return null;
}
}
}
log.error("{} not found.", name);
return null;
}
/**
* Adds schema node when different revision of node has received.
*
* @param schemaNode schema node
*/
private void addSchemaNodeUsingSchemaNameWithRev(
YangSchemaNode schemaNode) {
String date = getDateInStringFormat(schemaNode);
String name = schemaNode.getName();
if (!date.equals(EMPTY_STRING)) {
name = name + AT + date;
}
//check if already present.
if (!yangSchemaStore.containsKey(schemaNode.getName())) {
ysrContextForSchemaStore.curNode(schemaNode);
//if revision is not present no need to add in revision store.
ysrContextForSchemaStore
.addSchemaNodeWithRevisionStore(name, schemaNode);
yangSchemaStore.put(schemaNode.getName(),
ysrContextForSchemaStore);
} else {
YsrAppContext appContext =
yangSchemaStore.get(schemaNode.getName());
appContext.addSchemaNodeWithRevisionStore(name, schemaNode);
appContext.curNode(schemaNode);
}
}
/**
* Returns date in string format.
*
* @param schemaNode schema node
* @return date in string format
*/
String getDateInStringFormat(YangSchemaNode schemaNode) {
if (schemaNode != null) {
if (((YangNode) schemaNode).getRevision() != null) {
return new SimpleDateFormat(DATE_FORMAT)
.format(((YangNode) schemaNode).getRevision()
.getRevDate());
}
}
return EMPTY_STRING;
}
/**
* Removes schema node from schema map.
*
* @param removableNode schema node which needs to be removed
*/
private void removeSchemaNode(YangSchemaNode removableNode) {
String name = removableNode.getName();
String date = getDateInStringFormat(removableNode);
if (!date.isEmpty()) {
name = removableNode.getName() + AT +
getDateInStringFormat(removableNode);
}
YsrAppContext appContext = yangSchemaStore
.get(removableNode.getName());
if (appContext != null &&
!appContext.getYangSchemaNodeForRevisionStore().isEmpty() &&
appContext.getYangSchemaNodeForRevisionStore().size() != 1) {
appContext.removeSchemaNodeForRevisionStore(name);
} else {
yangSchemaStore.remove(removableNode.getName());
}
}
/**
* Verifies if the manager object is already registered with notification
* handler.
*
* @param serviceClass service class
* @return true if the manager object is already registered with
* notification handler
*/
public boolean verifyNotificationObject(Class<?> serviceClass) {
YangSchemaNode schemaNode = null;
String serviceName = serviceClass.getName();
if (appObjectStore.containsKey(serviceName)) {
schemaNode = getYangSchemaNodeUsingAppName(serviceName);
} else if (yangSchemaStoreForRootInterface.containsKey(serviceName)) {
schemaNode =
getYangSchemaNodeUsingGeneratedRootNodeInterfaceFileName(
serviceName);
} else if (yangSchemaStoreForRootOpParam.containsKey(serviceName)) {
schemaNode = getYangSchemaNodeUsingGeneratedRootNodeOpPramFileName(
serviceName);
}
if (schemaNode != null) {
String name = getEventClassName(schemaNode);
YsrAppContext appContext =
yangRootSchemaStoreForNotification.get(name);
if (appContext != null && !appContext.isNotificationRegistered()) {
appContext.setNotificationRegistered(true);
return true;
}
}
return false;
}
/**
* Returns schema node's generated interface class name.
*
* @param schemaNode schema node
* @return schema node's generated interface class name
*/
private String getInterfaceClassName(YangSchemaNode schemaNode) {
return schemaNode.getJavaPackage() + PERIOD +
getCapitalCase(schemaNode.getJavaClassNameOrBuiltInType());
}
/**
* Returns schema node's generated op param class name.
*
* @param schemaNode schema node
* @return schema node's generated op param class name
*/
private String getOpParamClassName(YangSchemaNode schemaNode) {
return getInterfaceClassName(schemaNode) + OP_PARAM;
}
/**
* Returns schema node's generated op param class name.
*
* @param schemaNode schema node
* @return schema node's generated op param class name
*/
private String getDefaultClassName(YangSchemaNode schemaNode) {
return schemaNode.getJavaPackage() + PERIOD + getCapitalCase(DEFAULT) +
getCapitalCase(schemaNode.getJavaClassNameOrBuiltInType());
}
/**
* Returns schema node's generated event class name.
*
* @param schemaNode schema node
* @return schema node's generated event class name
*/
private String getEventClassName(YangSchemaNode schemaNode) {
return getInterfaceClassName(schemaNode).toLowerCase() + PERIOD +
getCapitalCase(schemaNode.getJavaClassNameOrBuiltInType()) +
EVENT_STRING;
}
/**
* Returns schema node's generated service class name.
*
* @param schemaNode schema node
* @return schema node's generated service class name
*/
private String getServiceName(YangSchemaNode schemaNode) {
return getInterfaceClassName(schemaNode) + SERVICE;
}
/**
* Returns YSR application context for schema map.
*
* @return YSR application context for schema map
*/
YsrAppContext ysrContextForSchemaStore() {
return ysrContextForSchemaStore;
}
/**
* Sets YSR application context for schema map.
*
* @param context YSR application context for
* schema map
*/
void ysrContextForSchemaStore(YsrAppContext context) {
ysrContextForSchemaStore = context;
}
/**
* Returns YSR app context for application store.
*
* @return YSR app context for application store
*/
YsrAppContext ysrContextForAppStore() {
return ysrContextForAppStore;
}
/**
* Retrieves schema node from the store and deletes jar file path.
*
* @param appName application name
* @param store YSR stores
* @param appObject applications object
* @return schema node from the store
*/
private YangSchemaNode retrieveNodeForUnregister(
String appName,
ConcurrentMap<String, YsrAppContext> store, Object appObject) {
YsrAppContext curContext = store.get(appName);
boolean isValidObject;
if (curContext != null) {
isValidObject = verifyAppObject(appObject, curContext.appObject());
if (isValidObject) {
YangSchemaNode curNode = curContext.curNode();
//Delete all the generated ysr information in application's
// package.
removeYsrGeneratedTemporaryResources(curContext.jarPath(),
appName);
return curNode;
}
}
return null;
}
/**
* Verifies the application object which needs to be unregistered.
*
* @param appObject current received application object
* @param context stored application object
* @return true if objects are equal
*/
private boolean verifyAppObject(Object appObject, Object context) {
if (appObject != null && context != null) {
return appObject.equals(context);
}
return appObject == null && context == null;
}
/**
* Removes YSR generated temporary resources.
*
* @param rscPath resource path
* @param appName application name
*/
private void removeYsrGeneratedTemporaryResources(String rscPath,
String appName) {
if (rscPath != null) {
File jarPath = new File(rscPath);
if (jarPath.exists()) {
try {
deleteDirectory(jarPath);
} catch (IOException e) {
log.error("failed to delete ysr resources for {} : {}",
appName, e.getLocalizedMessage());
}
}
}
}
/**
* Removes from YANG schema store.
*
* @param curNode schema node
*/
private void removeFromYangSchemaStore(YangSchemaNode curNode) {
removeSchemaNode(curNode);
}
/**
* Removes from YANG schema notification store.
*
* @param curNode schema node
*/
private void removeFromYangNotificationStore(YangSchemaNode curNode) {
yangRootSchemaStoreForNotification
.remove(getEventClassName(curNode));
}
/**
* Removes from app store.
*
* @param appName application name
*/
private void removeFromAppSchemaStore(String appName) {
appObjectStore.remove(appName);
}
/**
* Removes from interface store.
*
* @param appName application name
*/
private void removeFromYangSchemaNodeForRootInterface(String appName) {
yangSchemaStoreForRootInterface.remove(appName);
}
/**
* Removes from op param store.
*
* @param appName application name
*/
private void removeFromYangSchemaNodeForRootOpParam(String appName) {
yangSchemaStoreForRootOpParam.remove(appName + OP_PARAM);
}
/**
* Removes YANG file information from file store.
*
* @param schemaNode schema node
*/
private void removeYangFileInfoFromStore(YangSchemaNode schemaNode) {
yangFileStore.remove(getModuleIdentifier(schemaNode));
}
/**
* Verifies if class with given name exists.
*
* @param appName application name
* @return true if class exists
*/
boolean verifyClassExistence(String appName) {
try {
classLoader.loadClass(appName);
return true;
} catch (ClassNotFoundException e) {
return false;
}
}
/**
* Clears database for YSR.
*/
public void flushYsrData() {
appObjectStore.clear();
yangSchemaStore.clear();
yangRootSchemaStoreForNotification.clear();
yangSchemaStoreForRootOpParam.clear();
yangSchemaStoreForRootInterface.clear();
registerClassStore.clear();
yangFileStore.clear();
}
/**
* Sets class loader of registered class.
*
* @param classLoader class loader of registered class
*/
void setClassLoader(ClassLoader classLoader) {
this.classLoader = classLoader;
}
/**
* Process module library for a registered service.
*
* @param node YANG schema nodes
*/
private void processModuleLibrary(YangNode node) {
YangModuleInformation moduleInformation =
new DefaultYangModuleInformation(getModuleIdentifier(node),
node.getNameSpace());
addSubModuleIdentifier(node, (
DefaultYangModuleInformation) moduleInformation);
//TODO: add feature list to module information.
((DefaultYangModuleLibrary) library)
.addModuleInformation(moduleInformation);
}
/**
* Adds sub module identifier.
*
* @param node schema node
* @param information module information
*/
private void addSubModuleIdentifier(
YangSchemaNode node, DefaultYangModuleInformation information) {
List<YangInclude> includeList = new ArrayList<>();
if (node instanceof YangModule) {
includeList = ((YangModule) node).getIncludeList();
} else if (node instanceof YangSubModule) {
includeList = ((YangSubModule) node).getIncludeList();
}
for (YangInclude include : includeList) {
information.addSubModuleIdentifiers(getModuleIdentifier(
include.getIncludedNode()));
}
}
/**
* Returns module identifier for schema node.
*
* @param schemaNode schema node
* @return module identifier for schema node
*/
private YangModuleIdentifier getModuleIdentifier(
YangSchemaNode schemaNode) {
return new DefaultYangModuleIdentifier(
schemaNode.getName(), getDateInStringFormat(schemaNode));
}
/**
* Returns module library.
*
* @return module library
*/
public YangModuleLibrary getLibrary() {
return library;
}
}