You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@camel.apache.org by da...@apache.org on 2014/06/26 20:08:44 UTC

[3/4] git commit: CAMEL-7546: Avoid clash of CamelContext managementName in OSGi. Also reuse clash logic in finding free default context name and context management name.

CAMEL-7546: Avoid clash of CamelContext managementName in OSGi. Also reuse clash logic in finding free default context name and context management name.


Project: http://git-wip-us.apache.org/repos/asf/camel/repo
Commit: http://git-wip-us.apache.org/repos/asf/camel/commit/67548e2e
Tree: http://git-wip-us.apache.org/repos/asf/camel/tree/67548e2e
Diff: http://git-wip-us.apache.org/repos/asf/camel/diff/67548e2e

Branch: refs/heads/camel-2.13.x
Commit: 67548e2ed2c68cd2a5601ba0c89f2758942e78b3
Parents: 0164fbc
Author: Claus Ibsen <da...@apache.org>
Authored: Thu Jun 26 18:44:51 2014 +0200
Committer: Claus Ibsen <da...@apache.org>
Committed: Thu Jun 26 20:08:16 2014 +0200

----------------------------------------------------------------------
 .../core/osgi/OsgiCamelContextNameStrategy.java | 42 +--------
 .../core/osgi/OsgiCamelContextPublisher.java    | 28 ++++--
 .../core/osgi/OsgiManagementNameStrategy.java   |  7 ++
 .../camel/core/osgi/OsgiNamingHelper.java       | 91 ++++++++++++++++++++
 4 files changed, 123 insertions(+), 45 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/camel/blob/67548e2e/components/camel-core-osgi/src/main/java/org/apache/camel/core/osgi/OsgiCamelContextNameStrategy.java
----------------------------------------------------------------------
diff --git a/components/camel-core-osgi/src/main/java/org/apache/camel/core/osgi/OsgiCamelContextNameStrategy.java b/components/camel-core-osgi/src/main/java/org/apache/camel/core/osgi/OsgiCamelContextNameStrategy.java
index a68c242..9e66e29 100644
--- a/components/camel-core-osgi/src/main/java/org/apache/camel/core/osgi/OsgiCamelContextNameStrategy.java
+++ b/components/camel-core-osgi/src/main/java/org/apache/camel/core/osgi/OsgiCamelContextNameStrategy.java
@@ -18,13 +18,8 @@ package org.apache.camel.core.osgi;
 
 import java.util.concurrent.atomic.AtomicInteger;
 
-import org.apache.camel.CamelContext;
 import org.apache.camel.spi.CamelContextNameStrategy;
 import org.osgi.framework.BundleContext;
-import org.osgi.framework.InvalidSyntaxException;
-import org.osgi.framework.ServiceReference;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
 
 import static org.apache.camel.core.osgi.OsgiCamelContextPublisher.CONTEXT_NAME_PROPERTY;
 
@@ -37,7 +32,6 @@ import static org.apache.camel.core.osgi.OsgiCamelContextPublisher.CONTEXT_NAME_
  */
 public class OsgiCamelContextNameStrategy implements CamelContextNameStrategy {
 
-    private static final Logger LOG = LoggerFactory.getLogger(OsgiCamelContextNameStrategy.class);
     private static final AtomicInteger CONTEXT_COUNTER = new AtomicInteger(0);
     private final BundleContext context;
     private final String prefix = "camel";
@@ -57,35 +51,8 @@ public class OsgiCamelContextNameStrategy implements CamelContextNameStrategy {
 
     @Override
     public synchronized String getNextName() {
-        String candidate = null;
-        boolean clash = false;
-
-        do {
-            try {
-                clash = false;
-
-                // generate new candidate
-                candidate = prefix + "-" + getNextCounter();
-                LOG.trace("Checking OSGi Service Registry for existence of existing CamelContext with name: {}", candidate);
-
-                ServiceReference[] refs = context.getServiceReferences(CamelContext.class.getName(), "(" + CONTEXT_NAME_PROPERTY + "=" + candidate + ")");
-                if (refs != null && refs.length > 0) {
-                    for (ServiceReference ref : refs) {
-                        Object id = ref.getProperty(CONTEXT_NAME_PROPERTY);
-                        if (id != null && candidate.equals(id)) {
-                            clash = true;
-                            break;
-                        }
-                    }
-                }
-            } catch (InvalidSyntaxException e) {
-                LOG.debug("Error finding free Camel name in OSGi Service Registry due " + e.getMessage() + ". This exception is ignored.", e);
-                break;
-            }
-        } while (clash);
-
-        LOG.debug("Generated CamelContext name for bundle id: {}, clash: {} -> {}", new Object[]{context.getBundle().getBundleId(), clash, candidate});
-        return candidate;
+        // false = do no check fist, but add the counter asap, so we have camel-1
+        return OsgiNamingHelper.findFreeCamelContextName(context, prefix, CONTEXT_NAME_PROPERTY, CONTEXT_COUNTER, false);
     }
 
     @Override
@@ -93,9 +60,4 @@ public class OsgiCamelContextNameStrategy implements CamelContextNameStrategy {
         return false;
     }
 
-    public static int getNextCounter() {
-        // we want to start counting from 1, so increment first
-        return CONTEXT_COUNTER.incrementAndGet();
-    }
-
 }

http://git-wip-us.apache.org/repos/asf/camel/blob/67548e2e/components/camel-core-osgi/src/main/java/org/apache/camel/core/osgi/OsgiCamelContextPublisher.java
----------------------------------------------------------------------
diff --git a/components/camel-core-osgi/src/main/java/org/apache/camel/core/osgi/OsgiCamelContextPublisher.java b/components/camel-core-osgi/src/main/java/org/apache/camel/core/osgi/OsgiCamelContextPublisher.java
index d932550..02eeb8e 100644
--- a/components/camel-core-osgi/src/main/java/org/apache/camel/core/osgi/OsgiCamelContextPublisher.java
+++ b/components/camel-core-osgi/src/main/java/org/apache/camel/core/osgi/OsgiCamelContextPublisher.java
@@ -43,6 +43,7 @@ public class OsgiCamelContextPublisher extends EventNotifierSupport {
     public static final String CONTEXT_SYMBOLIC_NAME_PROPERTY = "camel.context.symbolicname";
     public static final String CONTEXT_VERSION_PROPERTY = "camel.context.version";
     public static final String CONTEXT_NAME_PROPERTY = "camel.context.name";
+    public static final String CONTEXT_MANAGEMENT_NAME_PROPERTY = "camel.context.managementname";
 
     private final BundleContext bundleContext;
     private final Map<CamelContext, ServiceRegistration> registrations = new ConcurrentHashMap<CamelContext, ServiceRegistration>();
@@ -96,16 +97,19 @@ public class OsgiCamelContextPublisher extends EventNotifierSupport {
         // we must include unique camel management name so the symbolic name becomes unique,
         // in case the bundle has more than one CamelContext
         String name = camelContext.getName();
-        String symbolicName = bundleContext.getBundle().getSymbolicName() + "-" + name;
-        Version bundleVersion = getBundleVersion(bundleContext.getBundle());
-        ServiceReference[] refs = bundleContext.getServiceReferences(CamelContext.class.getName(),
-                "(&(" + CONTEXT_SYMBOLIC_NAME_PROPERTY + "=" + symbolicName + ")(" + CONTEXT_VERSION_PROPERTY + "=" + bundleVersion + "))");
+        String managementName = camelContext.getManagementName();
+        String symbolicName = bundleContext.getBundle().getSymbolicName();
+
+        if (!lookupCamelContext(bundleContext, symbolicName, name)) {
+            Version bundleVersion = getBundleVersion(bundleContext.getBundle());
 
-        if (refs == null) {
             Dictionary<String, Object > props = new Hashtable<String, Object>();
             props.put(CONTEXT_SYMBOLIC_NAME_PROPERTY, symbolicName);
             props.put(CONTEXT_VERSION_PROPERTY, bundleVersion);
             props.put(CONTEXT_NAME_PROPERTY, name);
+            if (managementName != null) {
+                props.put(CONTEXT_MANAGEMENT_NAME_PROPERTY, managementName);
+            }
 
             if (log.isDebugEnabled()) {
                 log.debug("Registering CamelContext [{}] of in OSGi registry", camelContext.getName());
@@ -127,4 +131,18 @@ public class OsgiCamelContextPublisher extends EventNotifierSupport {
         return (version != null) ? Version.parseVersion(version) : Version.emptyVersion;
     }
 
+    /**
+     * Lookup in the OSGi Service Registry whether a {@link org.apache.camel.CamelContext} is already registered with the given symbolic name.
+     *
+     * @return <tt>true</tt> if exists, <tt>false</tt> otherwise
+     */
+    public static boolean lookupCamelContext(BundleContext bundleContext, String symbolicName, String contextName) throws InvalidSyntaxException {
+        Version bundleVersion = getBundleVersion(bundleContext.getBundle());
+        ServiceReference[] refs = bundleContext.getServiceReferences(CamelContext.class.getName(),
+                "(&(" + CONTEXT_SYMBOLIC_NAME_PROPERTY + "=" + symbolicName + ")"
+                + "(" + CONTEXT_NAME_PROPERTY + "=" + contextName + ")"
+                + "(" + CONTEXT_VERSION_PROPERTY + "=" + bundleVersion + "))");
+        return refs != null && refs.length > 0;
+    }
+
 }

http://git-wip-us.apache.org/repos/asf/camel/blob/67548e2e/components/camel-core-osgi/src/main/java/org/apache/camel/core/osgi/OsgiManagementNameStrategy.java
----------------------------------------------------------------------
diff --git a/components/camel-core-osgi/src/main/java/org/apache/camel/core/osgi/OsgiManagementNameStrategy.java b/components/camel-core-osgi/src/main/java/org/apache/camel/core/osgi/OsgiManagementNameStrategy.java
index f870ca2..78468c6 100644
--- a/components/camel-core-osgi/src/main/java/org/apache/camel/core/osgi/OsgiManagementNameStrategy.java
+++ b/components/camel-core-osgi/src/main/java/org/apache/camel/core/osgi/OsgiManagementNameStrategy.java
@@ -16,6 +16,7 @@
  */
 package org.apache.camel.core.osgi;
 
+import java.util.concurrent.atomic.AtomicInteger;
 import java.util.regex.Matcher;
 
 import org.apache.camel.CamelContext;
@@ -41,6 +42,7 @@ import org.osgi.framework.BundleContext;
  */
 public class OsgiManagementNameStrategy extends DefaultManagementNameStrategy {
 
+    private static final AtomicInteger CONTEXT_COUNTER = new AtomicInteger(0);
     private final BundleContext bundleContext;
 
     public OsgiManagementNameStrategy(CamelContext camelContext, BundleContext bundleContext) {
@@ -62,6 +64,11 @@ public class OsgiManagementNameStrategy extends DefaultManagementNameStrategy {
         answer = answer.replaceFirst("#bundleId#", bundleId);
         answer = answer.replaceFirst("#symbolicName#", symbolicName);
         answer = answer.replaceFirst("#version#", version);
+
+        // we got a candidate then find a free name
+        // true = check fist if the candidate as-is is free, if not then use the counter
+        answer = OsgiNamingHelper.findFreeCamelContextName(bundleContext, answer, OsgiCamelContextPublisher.CONTEXT_MANAGEMENT_NAME_PROPERTY, CONTEXT_COUNTER, true);
+
         return answer;
     }
     

http://git-wip-us.apache.org/repos/asf/camel/blob/67548e2e/components/camel-core-osgi/src/main/java/org/apache/camel/core/osgi/OsgiNamingHelper.java
----------------------------------------------------------------------
diff --git a/components/camel-core-osgi/src/main/java/org/apache/camel/core/osgi/OsgiNamingHelper.java b/components/camel-core-osgi/src/main/java/org/apache/camel/core/osgi/OsgiNamingHelper.java
new file mode 100644
index 0000000..5c41f34
--- /dev/null
+++ b/components/camel-core-osgi/src/main/java/org/apache/camel/core/osgi/OsgiNamingHelper.java
@@ -0,0 +1,91 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You 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.apache.camel.core.osgi;
+
+import java.util.concurrent.atomic.AtomicInteger;
+
+import org.apache.camel.CamelContext;
+import org.osgi.framework.BundleContext;
+import org.osgi.framework.InvalidSyntaxException;
+import org.osgi.framework.ServiceReference;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+/**
+ * A helper to find free names in the OSGi service registry.
+ */
+public final class OsgiNamingHelper {
+
+    private static final Logger LOG = LoggerFactory.getLogger(OsgiNamingHelper.class);
+
+    private OsgiNamingHelper() {
+    }
+
+    /**
+     * Checks the OSGi service registry for a free name (uses the counter if there is a clash to find next free name)
+     *
+     * @param context the bundle context
+     * @param prefix  the prefix for the name
+     * @param key     the key to use in the OSGi filter; either {@link OsgiCamelContextPublisher#CONTEXT_NAME_PROPERTY}
+     *                or {@link OsgiCamelContextPublisher#CONTEXT_MANAGEMENT_NAME_PROPERTY}.
+     * @param counter the counter
+     * @param checkFirst <tt>true</tt> to check the prefix name as-is before using the counter, <tt>false</tt> the counter is used immediately
+     * @return the free name, is never <tt>null</tt>
+     */
+    public static String findFreeCamelContextName(BundleContext context, String prefix, String key, AtomicInteger counter, boolean checkFirst) {
+        String candidate = null;
+        boolean clash = false;
+
+        do {
+            try {
+                clash = false;
+
+                if (candidate == null && checkFirst) {
+                    // try candidate as-is
+                    candidate = prefix;
+                } else {
+                    // generate new candidate
+                    candidate = prefix + "-" + getNextCounter(counter);
+                }
+                LOG.trace("Checking OSGi Service Registry for existence of existing CamelContext with name: {}", candidate);
+
+                ServiceReference[] refs = context.getServiceReferences(CamelContext.class.getName(), "(" + key + "=" + candidate + ")");
+                if (refs != null && refs.length > 0) {
+                    for (ServiceReference ref : refs) {
+                        Object id = ref.getProperty(key);
+                        if (id != null && candidate.equals(id)) {
+                            clash = true;
+                            break;
+                        }
+                    }
+                }
+            } catch (InvalidSyntaxException e) {
+                LOG.debug("Error finding free Camel name in OSGi Service Registry due " + e.getMessage() + ". This exception is ignored.", e);
+                break;
+            }
+        } while (clash);
+
+        LOG.debug("Generated free name for bundle id: {}, clash: {} -> {}", new Object[]{context.getBundle().getBundleId(), clash, candidate});
+        return candidate;
+    }
+
+    public static int getNextCounter(AtomicInteger counter) {
+        // we want to start counting from 1, so increment first
+        return counter.incrementAndGet();
+    }
+
+}