summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDaniel Figueiredo Caetano2013-09-13 11:34:18 (EDT)
committer Samuel Padgett2013-09-18 16:53:20 (EDT)
commit695f24ea3bfd4ff680450392df65e2f0d373db2c (patch)
tree9f6e5a72234f525f750132e0680aae273bf76ec3
parentb79a8f9f3d4f898d1bf872991bec112f7861faf7 (diff)
downloadorg.eclipse.lyo.core-695f24ea3bfd4ff680450392df65e2f0d373db2c.zip
org.eclipse.lyo.core-695f24ea3bfd4ff680450392df65e2f0d373db2c.tar.gz
org.eclipse.lyo.core-695f24ea3bfd4ff680450392df65e2f0d373db2c.tar.bz2
Bug 416659 - Added support to global and custom namespace mappings.refs/changes/16/16416/2
Change-Id: I547b8f39fb4d03aab3a5b65b39165248cc2206a0 Signed-off-by: Daniel Figueiredo Caetano <dcaetano@br.ibm.com>
-rw-r--r--org.eclipse.lyo.oslc4j.core/src/main/java/org/eclipse/lyo/oslc4j/core/OslcGlobalNamespaceProvider.java101
-rw-r--r--org.eclipse.lyo.oslc4j.core/src/main/java/org/eclipse/lyo/oslc4j/core/annotation/OslcSchema.java27
-rw-r--r--org.eclipse.lyo.oslc4j.core/src/main/java/org/eclipse/lyo/oslc4j/core/model/IOslcCustomNamespaceProvider.java46
-rw-r--r--org.eclipse.lyo.oslc4j.provider.jena/src/main/java/org/eclipse/lyo/oslc4j/provider/jena/JenaModelHelper.java24
-rw-r--r--org.eclipse.lyo.oslc4j.provider.json4j/src/org/eclipse/lyo/oslc4j/provider/json4j/JsonHelper.java36
5 files changed, 225 insertions, 9 deletions
diff --git a/org.eclipse.lyo.oslc4j.core/src/main/java/org/eclipse/lyo/oslc4j/core/OslcGlobalNamespaceProvider.java b/org.eclipse.lyo.oslc4j.core/src/main/java/org/eclipse/lyo/oslc4j/core/OslcGlobalNamespaceProvider.java
new file mode 100644
index 0000000..d23d3db
--- /dev/null
+++ b/org.eclipse.lyo.oslc4j.core/src/main/java/org/eclipse/lyo/oslc4j/core/OslcGlobalNamespaceProvider.java
@@ -0,0 +1,101 @@
+/*******************************************************************************
+ * Copyright (c) 2013 IBM Corporation.
+ *
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * and Eclipse Distribution License v. 1.0 which accompanies this distribution.
+ *
+ * The Eclipse Public License is available at http://www.eclipse.org/legal/epl-v10.html
+ * and the Eclipse Distribution License is available at
+ * http://www.eclipse.org/org/documents/edl-v10.php.
+ *
+ * Contributors:
+ *
+ * Daniel Figueiredo Caetano - custom namespace provider
+ *******************************************************************************/
+package org.eclipse.lyo.oslc4j.core;
+
+import java.util.HashMap;
+import java.util.Map;
+
+import org.eclipse.lyo.oslc4j.core.annotation.OslcSchema;
+
+/**
+ * Defines the global namespace prefix mappings.
+ * The global namespace mappings do not take precedence
+ * over any other namespace mappings definition, which means
+ * that in case of conflict the {@link OslcSchema} will
+ * override the prefix.
+ *
+ * This class is a singleton instance, that can be obtained
+ * calling {@link #getInstance()}, since it works with
+ * any request even if there are no annotation mapping.
+ *
+ * @author Daniel Figueiredo Caetano
+ *
+ */
+public class OslcGlobalNamespaceProvider {
+
+ private static OslcGlobalNamespaceProvider instance;
+
+ private Map<String, String> prefixDefinitionMap;
+
+ /**
+ * Private construct for singleton pattern.
+ */
+ private OslcGlobalNamespaceProvider()
+ {
+ this.prefixDefinitionMap = new HashMap<String, String>();
+ }
+
+ /**
+ * Gets the unique instance of this class.
+ * @return singleton class instance.
+ */
+ public static OslcGlobalNamespaceProvider getInstance()
+ {
+ if(null == instance) {
+ synchronized (OslcGlobalNamespaceProvider.class) {
+ if(null == instance) {
+ instance = new OslcGlobalNamespaceProvider();
+ }
+ }
+ }
+ return instance;
+ }
+
+ /**
+ * Gets the Global namespace mappings, these mappings are
+ * applied to all operations, even without the annotation
+ * mappings.
+ *
+ * key - prefix
+ * value - namespace
+ *
+ * @return empty hash map instance if there are no global
+ * namespace mappings.
+ */
+ public Map<String, String> getPrefixDefinitionMap()
+ {
+ return prefixDefinitionMap;
+ }
+
+ /**
+ * Sets the global prefix definition map with the given map.
+ * Note that this operation overrides the current map.
+ *
+ * @param prefixDefinitionMap that will replace the current.
+ */
+ public void setPrefixDefinitionMap(Map<String, String> prefixDefinitionMap)
+ {
+ if(null == prefixDefinitionMap)
+ {
+ this.prefixDefinitionMap.clear();
+ }
+ else
+ {
+ this.prefixDefinitionMap = prefixDefinitionMap;
+ }
+ }
+
+} \ No newline at end of file
diff --git a/org.eclipse.lyo.oslc4j.core/src/main/java/org/eclipse/lyo/oslc4j/core/annotation/OslcSchema.java b/org.eclipse.lyo.oslc4j.core/src/main/java/org/eclipse/lyo/oslc4j/core/annotation/OslcSchema.java
index 439a424..1959498 100644
--- a/org.eclipse.lyo.oslc4j.core/src/main/java/org/eclipse/lyo/oslc4j/core/annotation/OslcSchema.java
+++ b/org.eclipse.lyo.oslc4j.core/src/main/java/org/eclipse/lyo/oslc4j/core/annotation/OslcSchema.java
@@ -1,5 +1,5 @@
/*******************************************************************************
- * Copyright (c) 2012 IBM Corporation.
+ * Copyright (c) 2012, 2013 IBM Corporation.
*
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
@@ -11,10 +11,11 @@
*
* Contributors:
*
- * Russell Boykin - initial API and implementation
- * Alberto Giammaria - initial API and implementation
- * Chris Peters - initial API and implementation
- * Gianluca Bernardini - initial API and implementation
+ * Russell Boykin - initial API and implementation
+ * Alberto Giammaria - initial API and implementation
+ * Chris Peters - initial API and implementation
+ * Gianluca Bernardini - initial API and implementation
+ * Daniel Figueiredo Caetano - custom namespace provider
*******************************************************************************/
package org.eclipse.lyo.oslc4j.core.annotation;
@@ -23,11 +24,25 @@ import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
+import org.eclipse.lyo.oslc4j.core.model.IOslcCustomNamespaceProvider;
+
@Target(ElementType.PACKAGE)
@Retention(RetentionPolicy.RUNTIME)
public @interface OslcSchema {
- /**
+
+ /**
* The namespace mappings for the package.
*/
OslcNamespaceDefinition[] value();
+
+ /**
+ * Any class that implements the {@link IOslcCustomNamespaceProvider}.
+ * This must be a concrete implementation and have a public no args constructor.
+ *
+ * @return {@link IOslcCustomNamespaceProvider} .class is the default value,
+ * because this field must not be required and since it is not a concrete
+ * implementation of the interface it will be ignored.
+ */
+ Class<? extends IOslcCustomNamespaceProvider> customNamespaceProvider() default IOslcCustomNamespaceProvider.class;
+
}
diff --git a/org.eclipse.lyo.oslc4j.core/src/main/java/org/eclipse/lyo/oslc4j/core/model/IOslcCustomNamespaceProvider.java b/org.eclipse.lyo.oslc4j.core/src/main/java/org/eclipse/lyo/oslc4j/core/model/IOslcCustomNamespaceProvider.java
new file mode 100644
index 0000000..b8bb2fa
--- /dev/null
+++ b/org.eclipse.lyo.oslc4j.core/src/main/java/org/eclipse/lyo/oslc4j/core/model/IOslcCustomNamespaceProvider.java
@@ -0,0 +1,46 @@
+/*******************************************************************************
+ * Copyright (c) 2013 IBM Corporation.
+ *
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * and Eclipse Distribution License v. 1.0 which accompanies this distribution.
+ *
+ * The Eclipse Public License is available at http://www.eclipse.org/legal/epl-v10.html
+ * and the Eclipse Distribution License is available at
+ * http://www.eclipse.org/org/documents/edl-v10.php.
+ *
+ * Contributors:
+ *
+ * Daniel Figueiredo Caetano - custom namespace provider
+ *******************************************************************************/
+package org.eclipse.lyo.oslc4j.core.model;
+
+import java.util.Map;
+
+import org.eclipse.lyo.oslc4j.core.annotation.OslcSchema;
+
+/**
+ * This interface provides a way to add custom prefixes at runtime. As it is
+ * used inside the {@link OslcSchema} annotation, <b>every time</b> that this annotation
+ * is read during the response writing it is also checked for a class definition in
+ * the {@link OslcSchema#customNamespaceProvider()} field and if there is a concrete
+ * implementation of this interface, a new instance of this implementation will be created
+ * and the {@link #getCustomNamespacePrefixes()} invoked.
+ *
+ * All values obtained will be added to the namespace prefix list, thereafter used in
+ * the response writing. Note that if the {@link #getCustomNamespacePrefixes()} map, hereafter
+ * called customMap, contains keys that are equal to the ones defined in
+ * {@link OslcSchema#value()}, the customMap's key=value will take precedence over the others.
+ *
+ * @author Daniel Figueiredo Caetano
+ * @see OslcSchema
+ */
+public interface IOslcCustomNamespaceProvider {
+
+ /**
+ * Gets a map where the key = prefix and value = namespace.
+ * @return null if there are no custom prefixes to add.
+ */
+ Map<String, String> getCustomNamespacePrefixes();
+
+} \ No newline at end of file
diff --git a/org.eclipse.lyo.oslc4j.provider.jena/src/main/java/org/eclipse/lyo/oslc4j/provider/jena/JenaModelHelper.java b/org.eclipse.lyo.oslc4j.provider.jena/src/main/java/org/eclipse/lyo/oslc4j/provider/jena/JenaModelHelper.java
index 8351af7..e26afdd 100644
--- a/org.eclipse.lyo.oslc4j.provider.jena/src/main/java/org/eclipse/lyo/oslc4j/provider/jena/JenaModelHelper.java
+++ b/org.eclipse.lyo.oslc4j.provider.jena/src/main/java/org/eclipse/lyo/oslc4j/provider/jena/JenaModelHelper.java
@@ -65,6 +65,7 @@ import javax.xml.transform.stream.StreamResult;
import org.eclipse.lyo.oslc4j.core.NestedWildcardProperties;
import org.eclipse.lyo.oslc4j.core.OSLC4JConstants;
import org.eclipse.lyo.oslc4j.core.OSLC4JUtils;
+import org.eclipse.lyo.oslc4j.core.OslcGlobalNamespaceProvider;
import org.eclipse.lyo.oslc4j.core.SingletonWildcardProperties;
import org.eclipse.lyo.oslc4j.core.annotation.OslcName;
import org.eclipse.lyo.oslc4j.core.annotation.OslcNamespaceDefinition;
@@ -82,6 +83,7 @@ import org.eclipse.lyo.oslc4j.core.model.AbstractResource;
import org.eclipse.lyo.oslc4j.core.model.AnyResource;
import org.eclipse.lyo.oslc4j.core.model.FilteredResource;
import org.eclipse.lyo.oslc4j.core.model.IExtendedResource;
+import org.eclipse.lyo.oslc4j.core.model.IOslcCustomNamespaceProvider;
import org.eclipse.lyo.oslc4j.core.model.IReifiedResource;
import org.eclipse.lyo.oslc4j.core.model.IResource;
import org.eclipse.lyo.oslc4j.core.model.InheritedMethodAnnotationHelper;
@@ -273,7 +275,7 @@ public final class JenaModelHelper
OslcCoreApplicationException
{
final Class<? extends Object> objectClass = object.getClass();
-
+ namespaceMappings.putAll(OslcGlobalNamespaceProvider.getInstance().getPrefixDefinitionMap());
// Collect the namespace prefix -> namespace mappings
recursivelyCollectNamespaceMappings(namespaceMappings,
objectClass);
@@ -1930,6 +1932,26 @@ public final class JenaModelHelper
namespaceMappings.put(prefix,
namespaceURI);
}
+ //Adding custom prefixes obtained from an implementation, if there is an implementation.
+ Class<? extends IOslcCustomNamespaceProvider> customNamespaceProvider = oslcSchemaAnnotation.customNamespaceProvider();
+ if(!customNamespaceProvider.isInterface())
+ {
+ try {
+ IOslcCustomNamespaceProvider customNamespaceProviderImpl = customNamespaceProvider.newInstance();
+ Map<String, String> customNamespacePrefixes = customNamespaceProviderImpl.getCustomNamespacePrefixes();
+ if(null != customNamespacePrefixes)
+ {
+ namespaceMappings.putAll(customNamespacePrefixes);
+ }
+ } catch (IllegalAccessException e) {
+ throw new RuntimeException("The custom namespace provider implementation: "+
+ customNamespaceProvider.getClass().getName() +
+ ", must have a public no args construtor", e);
+ } catch (InstantiationException e) {
+ throw new RuntimeException("The custom namespace provider must not be a abstract, nor interface class and " +
+ "must have a public no args constructor", e);
+ }
+ }
}
final Class<?> superClass = resourceClass.getSuperclass();
diff --git a/org.eclipse.lyo.oslc4j.provider.json4j/src/org/eclipse/lyo/oslc4j/provider/json4j/JsonHelper.java b/org.eclipse.lyo.oslc4j.provider.json4j/src/org/eclipse/lyo/oslc4j/provider/json4j/JsonHelper.java
index b97eada..5885471 100644
--- a/org.eclipse.lyo.oslc4j.provider.json4j/src/org/eclipse/lyo/oslc4j/provider/json4j/JsonHelper.java
+++ b/org.eclipse.lyo.oslc4j.provider.json4j/src/org/eclipse/lyo/oslc4j/provider/json4j/JsonHelper.java
@@ -61,6 +61,7 @@ import org.apache.wink.json4j.JSONObject;
import org.eclipse.lyo.oslc4j.core.NestedWildcardProperties;
import org.eclipse.lyo.oslc4j.core.OSLC4JConstants;
import org.eclipse.lyo.oslc4j.core.OSLC4JUtils;
+import org.eclipse.lyo.oslc4j.core.OslcGlobalNamespaceProvider;
import org.eclipse.lyo.oslc4j.core.SingletonWildcardProperties;
import org.eclipse.lyo.oslc4j.core.annotation.OslcName;
import org.eclipse.lyo.oslc4j.core.annotation.OslcNamespaceDefinition;
@@ -78,6 +79,7 @@ import org.eclipse.lyo.oslc4j.core.exception.OslcCoreRelativeURIException;
import org.eclipse.lyo.oslc4j.core.model.AbstractResource;
import org.eclipse.lyo.oslc4j.core.model.AnyResource;
import org.eclipse.lyo.oslc4j.core.model.IExtendedResource;
+import org.eclipse.lyo.oslc4j.core.model.IOslcCustomNamespaceProvider;
import org.eclipse.lyo.oslc4j.core.model.IReifiedResource;
import org.eclipse.lyo.oslc4j.core.model.IResource;
import org.eclipse.lyo.oslc4j.core.model.InheritedMethodAnnotationHelper;
@@ -1273,7 +1275,12 @@ public final class JsonHelper
OslcCoreApplicationException
{
final Class<? extends Object> objectClass = object.getClass();
-
+ // Add all global namespace mappings, since they have lower precedence
+ Map<String, String> globalPrefixDefinitionMap = OslcGlobalNamespaceProvider.getInstance().getPrefixDefinitionMap();
+ for(Map.Entry<String, String> prefixDefinitionEntry : globalPrefixDefinitionMap.entrySet()) {
+ namespaceMappings.put(prefixDefinitionEntry.getKey(), prefixDefinitionEntry.getValue());
+ reverseNamespaceMappings.put(prefixDefinitionEntry.getValue(), prefixDefinitionEntry.getKey());
+ }
// Collect the namespace prefix -> namespace mappings
recursivelyCollectNamespaceMappings(namespaceMappings,
reverseNamespaceMappings,
@@ -1395,6 +1402,30 @@ public final class JsonHelper
reverseNamespaceMappings.put(namespaceURI,
prefix);
}
+ //Adding custom prefixes obtained from an implementation, if there is an implementation.
+ Class<? extends IOslcCustomNamespaceProvider> customNamespaceProvider = oslcSchemaAnnotation.customNamespaceProvider();
+ if(!customNamespaceProvider.isInterface())
+ {
+ try {
+ IOslcCustomNamespaceProvider customNamespaceProviderImpl = customNamespaceProvider.newInstance();
+ Map<String, String> customNamespacePrefixes = customNamespaceProviderImpl.getCustomNamespacePrefixes();
+ if(null != customNamespacePrefixes)
+ {
+ for(Map.Entry<String, String> namespaceEntry : customNamespacePrefixes.entrySet())
+ {
+ namespaceMappings.put(namespaceEntry.getKey(), namespaceEntry.getValue());
+ reverseNamespaceMappings.put(namespaceEntry.getValue(), namespaceEntry.getKey());
+ }
+ }
+ } catch (IllegalAccessException e) {
+ throw new RuntimeException("The custom namespace provider implementation: "+
+ customNamespaceProvider.getClass().getName() +
+ ", must have a public no args construtor", e);
+ } catch (InstantiationException e) {
+ throw new RuntimeException("The custom namespace provider must not be a abstract, nor interface class and " +
+ "must have a public no args constructor", e);
+ }
+ }
}
final Class<?> superClass = objectClass.getSuperclass();
@@ -2278,4 +2309,5 @@ public final class JsonHelper
return result;
}
-}
+
+} \ No newline at end of file