You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@karaf.apache.org by io...@apache.org on 2011/11/20 17:50:24 UTC

svn commit: r1204184 - in /karaf/cellar/trunk: assembly/ assembly/src/main/resources/ core/src/main/java/org/apache/karaf/cellar/core/discovery/ hazelcast/src/main/java/org/apache/karaf/cellar/hazelcast/factory/ hazelcast/src/main/resources/OSGI-INF/bl...

Author: iocanel
Date: Sun Nov 20 16:50:23 2011
New Revision: 1204184

URL: http://svn.apache.org/viewvc?rev=1204184&view=rev
Log:
[KARAF-850] Cellar now uses hazelcast.xml under etc folder to provide default Hazelcast configuration. Group and Network configuration are overrided by the configuration Admin.

Added:
    karaf/cellar/trunk/assembly/src/main/resources/hazelcast.xml
    karaf/cellar/trunk/hazelcast/src/main/java/org/apache/karaf/cellar/hazelcast/factory/HazelcastConfigurationManager.java
Modified:
    karaf/cellar/trunk/assembly/pom.xml
    karaf/cellar/trunk/assembly/src/main/resources/features.xml
    karaf/cellar/trunk/assembly/src/main/resources/groups.cfg
    karaf/cellar/trunk/core/src/main/java/org/apache/karaf/cellar/core/discovery/DiscoveryTask.java
    karaf/cellar/trunk/hazelcast/src/main/java/org/apache/karaf/cellar/hazelcast/factory/HazelcastServiceFactory.java
    karaf/cellar/trunk/hazelcast/src/main/resources/OSGI-INF/blueprint/blueprint.xml
    karaf/cellar/trunk/hazelcast/src/test/java/org/apache/karaf/cellar/hazelcast/factory/HazelcastServiceFactoryTest.java

Modified: karaf/cellar/trunk/assembly/pom.xml
URL: http://svn.apache.org/viewvc/karaf/cellar/trunk/assembly/pom.xml?rev=1204184&r1=1204183&r2=1204184&view=diff
==============================================================================
--- karaf/cellar/trunk/assembly/pom.xml (original)
+++ karaf/cellar/trunk/assembly/pom.xml Sun Nov 20 16:50:23 2011
@@ -95,6 +95,11 @@
                                     <type>cfg</type>
                                     <classifier>instance</classifier>
                                 </artifact>
+                                <artifact>
+                                    <file>target/classes/hazelcast.xml</file>
+                                    <type>xml</type>
+                                    <classifier>hazelcast</classifier>
+                                </artifact>
                             </artifacts>
                         </configuration>
                     </execution>

Modified: karaf/cellar/trunk/assembly/src/main/resources/features.xml
URL: http://svn.apache.org/viewvc/karaf/cellar/trunk/assembly/src/main/resources/features.xml?rev=1204184&r1=1204183&r2=1204184&view=diff
==============================================================================
--- karaf/cellar/trunk/assembly/src/main/resources/features.xml (original)
+++ karaf/cellar/trunk/assembly/src/main/resources/features.xml Sun Nov 20 16:50:23 2011
@@ -13,7 +13,7 @@
    See the License for the specific language governing permissions and
    limitations under the License.
 -->
-<features name="org.apache.karaf.cellar.features-${project.version}" xmlns="http://karaf.apache.org/xmlns/features/v1.0.0">
+<features name="cellar-${project.version}" xmlns="http://karaf.apache.org/xmlns/features/v1.0.0">
 
     <repository>mvn:org.jclouds.karaf/jclouds-karaf/${jclouds.karaf.version}/xml/features</repository>
 
@@ -48,6 +48,9 @@
         <configfile finalname="/etc/org.apache.karaf.cellar.node.cfg">
             mvn:org.apache.karaf.cellar/apache-karaf-cellar/${project.version}/cfg/node
         </configfile>
+        <configfile finalname="/etc/hazelcast.xml">
+            mvn:org.apache.karaf.cellar/apache-karaf-cellar/${project.version}/xml/hazelcast
+        </configfile>
     </feature>
 
     <feature name='cellar-obr' description='Alias to org.apache.karaf.cellar.features.obr feature' version='${project.version}' resolver='(obr)'>

Modified: karaf/cellar/trunk/assembly/src/main/resources/groups.cfg
URL: http://svn.apache.org/viewvc/karaf/cellar/trunk/assembly/src/main/resources/groups.cfg?rev=1204184&r1=1204183&r2=1204184&view=diff
==============================================================================
--- karaf/cellar/trunk/assembly/src/main/resources/groups.cfg (original)
+++ karaf/cellar/trunk/assembly/src/main/resources/groups.cfg Sun Nov 20 16:50:23 2011
@@ -17,5 +17,9 @@ default.features.blacklist.outbound=cell
 default.features.sync=true
 default.features.repositories.sync=true
 
+default.bundle.whitelist.inbound=
+default.bundle.whitelist.outbound=
+default.bundle.sync=false
+
 default.obr.urls.sync=true
 default.obr.bundles.sync=true
\ No newline at end of file

Added: karaf/cellar/trunk/assembly/src/main/resources/hazelcast.xml
URL: http://svn.apache.org/viewvc/karaf/cellar/trunk/assembly/src/main/resources/hazelcast.xml?rev=1204184&view=auto
==============================================================================
--- karaf/cellar/trunk/assembly/src/main/resources/hazelcast.xml (added)
+++ karaf/cellar/trunk/assembly/src/main/resources/hazelcast.xml Sun Nov 20 16:50:23 2011
@@ -0,0 +1,158 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<hazelcast xsi:schemaLocation="http://www.hazelcast.com/schema/config hazelcast-basic.xsd"
+           xmlns="http://www.hazelcast.com/schema/config"
+           xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
+    <group>
+        <name>dev</name>
+        <password>dev-pass</password>
+    </group>
+    <network>
+        <port auto-increment="true">5701</port>
+        <join>
+            <multicast enabled="true">
+                <multicast-group>224.2.2.3</multicast-group>
+                <multicast-port>54327</multicast-port>
+            </multicast>
+            <tcp-ip enabled="false">
+                <interface>127.0.0.1</interface>
+            </tcp-ip>
+            <aws enabled="false">
+                <access-key>my-access-key</access-key>
+                <secret-key>my-secret-key</secret-key>
+                <region>us-east-1</region>
+            </aws>
+        </join>
+        <interfaces enabled="false">
+            <interface>10.10.1.*</interface>
+        </interfaces>
+        <symmetric-encryption enabled="false">
+            <!--
+               encryption algorithm such as
+               DES/ECB/PKCS5Padding,
+               PBEWithMD5AndDES,
+               AES/CBC/PKCS5Padding,
+               Blowfish,
+               DESede
+            -->
+            <algorithm>PBEWithMD5AndDES</algorithm>
+            <!-- salt value to use when generating the secret key -->
+            <salt>thesalt</salt>
+            <!-- pass phrase to use when generating the secret key -->
+            <password>thepass</password>
+            <!-- iteration count to use when generating the secret key -->
+            <iteration-count>19</iteration-count>
+        </symmetric-encryption>
+        <asymmetric-encryption enabled="false">
+            <!-- encryption algorithm -->
+            <algorithm>RSA/NONE/PKCS1PADDING</algorithm>
+            <!-- private key password -->
+            <keyPassword>thekeypass</keyPassword>
+            <!-- private key alias -->
+            <keyAlias>local</keyAlias>
+            <!-- key store type -->
+            <storeType>JKS</storeType>
+            <!-- key store password -->
+            <storePassword>thestorepass</storePassword>
+            <!-- path to the key store -->
+            <storePath>keystore</storePath>
+        </asymmetric-encryption>
+    </network>
+    <executor-service>
+        <core-pool-size>16</core-pool-size>
+        <max-pool-size>64</max-pool-size>
+        <keep-alive-seconds>60</keep-alive-seconds>
+    </executor-service>
+    <queue name="default">
+        <!--
+            Maximum size of the queue. When a JVM's local queue size reaches the maximum,
+            all put/offer operations will get blocked until the queue size
+            of the JVM goes down below the maximum.
+            Any integer between 0 and Integer.MAX_VALUE. 0 means
+            Integer.MAX_VALUE. Default is 0.
+        -->
+        <max-size-per-jvm>0</max-size-per-jvm>
+        <!--
+            Name of the map configuration that will be used for the backing distributed
+            map for this queue.
+        -->
+        <backing-map-ref>default</backing-map-ref>
+    </queue>
+    <map name="default">
+        <!--
+            Number of backups. If 1 is set as the backup-count for example,
+            then all entries of the map will be copied to another JVM for
+            fail-safety. 0 means no backup.
+        -->
+        <backup-count>1</backup-count>
+        <!--
+			Maximum number of seconds for each entry to stay in the map. Entries that are
+			older than <time-to-live-seconds> and not updated for <time-to-live-seconds>
+			will get automatically evicted from the map.
+			Any integer between 0 and Integer.MAX_VALUE. 0 means infinite. Default is 0.
+		-->
+        <time-to-live-seconds>0</time-to-live-seconds>
+        <!--
+			Maximum number of seconds for each entry to stay idle in the map. Entries that are
+			idle(not touched) for more than <max-idle-seconds> will get
+			automatically evicted from the map. Entry is touched if get, put or containsKey is called.
+			Any integer between 0 and Integer.MAX_VALUE. 0 means infinite. Default is 0.
+		-->
+        <max-idle-seconds>0</max-idle-seconds>
+        <!--
+            Valid values are:
+            NONE (no eviction),
+            LRU (Least Recently Used),
+            LFU (Least Frequently Used).
+            NONE is the default.
+        -->
+        <eviction-policy>NONE</eviction-policy>
+        <!--
+            Maximum size of the map. When max size is reached,
+            map is evicted based on the policy defined.
+            Any integer between 0 and Integer.MAX_VALUE. 0 means
+            Integer.MAX_VALUE. Default is 0.
+        -->
+        <max-size policy="cluster_wide_map_size">0</max-size>
+        <!--
+            When max. size is reached, specified percentage of
+            the map will be evicted. Any integer between 0 and 100.
+            If 25 is set for example, 25% of the entries will
+            get evicted.
+        -->
+        <eviction-percentage>25</eviction-percentage>
+        <!--
+            While recovering from split-brain (network partitioning),
+            map entries in the small cluster will merge into the bigger cluster
+            based on the policy set here. When an entry merge into the
+            cluster, there might an existing entry with the same key already.
+            Values of these entries might be different for that same key.
+            Which value should be set for the key? Conflict is resolved by
+            the policy set here. Default policy is hz.ADD_NEW_ENTRY
+
+            There are built-in merge policies such as
+            hz.NO_MERGE      ; no entry will merge.
+            hz.ADD_NEW_ENTRY ; entry will be added if the merging entry's key
+                               doesn't exist in the cluster.
+            hz.HIGHER_HITS   ; entry with the higher hits wins.
+            hz.LATEST_UPDATE ; entry with the latest update wins.
+        -->
+        <merge-policy>hz.ADD_NEW_ENTRY</merge-policy>
+    </map>
+    <!-- Add your own semaphore configurations here:
+        <semaphore name="default">
+            <initial-permits>10</initial-permits>
+            <semaphore-factory enabled="true">
+                <class-name>com.acme.MySemaphoreFactory</class-name>
+            </semaphore-factory>
+        </semaphore>
+    -->
+
+    <!-- Add your own map merge policy implementations here:
+    	<merge-policies>
+           	<map-merge-policy name="MY_MERGE_POLICY">
+            	<class-name>com.acme.MyOwnMergePolicy</class-name>
+        	</map-merge-policy>
+    	</merge-policies>
+    -->
+
+</hazelcast>
\ No newline at end of file

Modified: karaf/cellar/trunk/core/src/main/java/org/apache/karaf/cellar/core/discovery/DiscoveryTask.java
URL: http://svn.apache.org/viewvc/karaf/cellar/trunk/core/src/main/java/org/apache/karaf/cellar/core/discovery/DiscoveryTask.java?rev=1204184&r1=1204183&r2=1204184&view=diff
==============================================================================
--- karaf/cellar/trunk/core/src/main/java/org/apache/karaf/cellar/core/discovery/DiscoveryTask.java (original)
+++ karaf/cellar/trunk/core/src/main/java/org/apache/karaf/cellar/core/discovery/DiscoveryTask.java Sun Nov 20 16:50:23 2011
@@ -13,17 +13,19 @@
  */
 package org.apache.karaf.cellar.core.discovery;
 
-import org.osgi.service.cm.Configuration;
-import org.osgi.service.cm.ConfigurationAdmin;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
 import java.io.IOException;
 import java.util.Dictionary;
 import java.util.Iterator;
 import java.util.LinkedHashSet;
 import java.util.List;
 import java.util.Set;
+import java.util.concurrent.Executors;
+import java.util.concurrent.ScheduledExecutorService;
+import java.util.concurrent.TimeUnit;
+import org.osgi.service.cm.Configuration;
+import org.osgi.service.cm.ConfigurationAdmin;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
 
 public class DiscoveryTask implements Runnable {
 
@@ -32,6 +34,16 @@ public class DiscoveryTask implements Ru
     private List<DiscoveryService> discoveryServices;
     private ConfigurationAdmin configurationAdmin;
 
+    private ScheduledExecutorService scheduler = Executors.newScheduledThreadPool(1);
+
+    public void init() {
+        scheduler.scheduleWithFixedDelay(this, 10, 10, TimeUnit.SECONDS);
+    }
+
+    public void destroy() {
+        scheduler.shutdown();
+    }
+
     @Override
     public void run() {
         LOGGER.trace("CELLAR DISCOVERY: Starting the discovery task.");

Added: karaf/cellar/trunk/hazelcast/src/main/java/org/apache/karaf/cellar/hazelcast/factory/HazelcastConfigurationManager.java
URL: http://svn.apache.org/viewvc/karaf/cellar/trunk/hazelcast/src/main/java/org/apache/karaf/cellar/hazelcast/factory/HazelcastConfigurationManager.java?rev=1204184&view=auto
==============================================================================
--- karaf/cellar/trunk/hazelcast/src/main/java/org/apache/karaf/cellar/hazelcast/factory/HazelcastConfigurationManager.java (added)
+++ karaf/cellar/trunk/hazelcast/src/main/java/org/apache/karaf/cellar/hazelcast/factory/HazelcastConfigurationManager.java Sun Nov 20 16:50:23 2011
@@ -0,0 +1,244 @@
+package org.apache.karaf.cellar.hazelcast.factory;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.LinkedHashSet;
+import java.util.Map;
+import java.util.Set;
+import com.hazelcast.config.Config;
+import com.hazelcast.config.GroupConfig;
+import com.hazelcast.config.MulticastConfig;
+import com.hazelcast.config.TcpIpConfig;
+import com.hazelcast.config.XmlConfigBuilder;
+import com.hazelcast.core.HazelcastInstance;
+import org.apache.karaf.cellar.core.discovery.Discovery;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+public class HazelcastConfigurationManager {
+
+    private static final transient Logger LOGGER = LoggerFactory.getLogger(HazelcastServiceFactory.class);
+
+    public static final String USERNAME="username";
+    public static final String PASSWORD="password";
+
+    public static final String MULTICAST_ENABLED="multicastEnabled";
+    public static final String MULTICAST_GROUP="multicastGroup";
+    public static final String MULTICAST_PORT="multicastPort";
+    public static final String MULTICAST_TIMEOUT_IN_SECONDS="multicastTimeoutSeconds";
+
+    public static final String TCPIP_ENABLED="tcpIpEnabled";
+    public static final String TCPIP_MEMBERS="tcpIpMembers";
+
+    private String username = GroupConfig.DEFAULT_GROUP_NAME;
+    private String password = GroupConfig.DEFAULT_GROUP_PASSWORD;
+
+    private boolean multicastEnabled = MulticastConfig.DEFAULT_ENABLED;
+    private String multicastGroup = MulticastConfig.DEFAULT_MULTICAST_GROUP;
+    private int multicastPort = MulticastConfig.DEFAULT_MULTICAST_PORT;
+    private int multicastTimeoutSeconds = MulticastConfig.DEFAULT_MULTICAST_TIMEOUT_SECONDS;
+
+    private boolean tcpIpEnabled = true;
+    private String tcpIpMembers = "";
+    private Set<String> tcpIpMemberSet = new LinkedHashSet<String>();
+    private Set<String> discoveredMemberSet = new LinkedHashSet<String>();
+
+    private String xmlConfigLocation = System.getProperty("karaf.home") + "/etc/hazelcast.xml";
+
+    /**
+     * Creates or Updates Hazelcast Instance.
+     *
+     * @param properties
+     */
+    public boolean isUpdated(Map properties) {
+            Boolean updated = Boolean.FALSE;
+            //We need it to properly instantiate Hazelcast.
+            if (properties != null) {
+                if (properties.containsKey(USERNAME)) {
+                    String newUsername = (String) properties.get(USERNAME);
+                    if (username != null && newUsername != null && !username.endsWith(newUsername)) {
+                        this.username = newUsername;
+                        updated = Boolean.TRUE;
+                    }
+                }
+
+                if (properties.containsKey(PASSWORD)) {
+                    String newPassword = (String) properties.get(PASSWORD);
+                    if (password != null && !password.equals(newPassword)) {
+                        this.password = newPassword;
+                        updated = Boolean.TRUE;
+                    }
+                }
+
+                Boolean newMulticastEnabled = Boolean.parseBoolean((String) properties.get(MULTICAST_ENABLED));
+                if (multicastEnabled != newMulticastEnabled) {
+                    this.multicastEnabled = newMulticastEnabled;
+                    updated = Boolean.TRUE;
+                }
+
+                if (properties.containsKey(MULTICAST_GROUP)) {
+                    String newMulticastGroup = (String) properties.get(MULTICAST_GROUP);
+                    if (multicastGroup != null && newMulticastGroup != null && !multicastGroup.endsWith(newMulticastGroup)) {
+                        this.multicastGroup = newMulticastGroup;
+                        updated = Boolean.TRUE;
+                    }
+
+                }
+
+                if (properties.containsKey(MULTICAST_PORT)) {
+                    try {
+                        int newMulticastPort = Integer.parseInt((String) properties.get(MULTICAST_PORT));
+                        if (multicastPort != 0 && multicastPort != newMulticastPort) {
+                            this.multicastPort = newMulticastPort;
+                            updated = Boolean.TRUE;
+                        }
+                    } catch (NumberFormatException ex) {
+                        LOGGER.warn("Could not parse port number", ex);
+                    }
+                }
+
+                if (properties.containsKey(MULTICAST_TIMEOUT_IN_SECONDS)) {
+                    try {
+                        int newMulticastTimeoutSeconds = Integer.parseInt((String) properties.get(MULTICAST_TIMEOUT_IN_SECONDS));
+                        if (multicastTimeoutSeconds != 0 && multicastTimeoutSeconds != newMulticastTimeoutSeconds) {
+                            this.multicastTimeoutSeconds = newMulticastTimeoutSeconds;
+                            updated = Boolean.TRUE;
+                        }
+                    } catch (NumberFormatException ex) {
+                        LOGGER.warn("Could not parse multicast timeout in seconds", ex);
+                    }
+                }
+
+                if (properties.containsKey(TCPIP_ENABLED)) {
+                    Boolean newTcpIpEnabled = Boolean.parseBoolean((String) properties.get(TCPIP_ENABLED));
+                    if (tcpIpEnabled != newTcpIpEnabled) {
+                        this.tcpIpEnabled = newTcpIpEnabled;
+                        updated = Boolean.TRUE;
+                    }
+                }
+
+                Set<String> newTcpIpMemberSet = createSetFromString((String) properties.get(TCPIP_MEMBERS));
+                if (tcpIpMemberSet != null && newTcpIpMemberSet != null && !collectionEquals(tcpIpMemberSet, newTcpIpMemberSet)) {
+                    tcpIpMemberSet = newTcpIpMemberSet;
+                    updated = Boolean.TRUE;
+                }
+
+                Set<String> newDiscoveredMemberSet = createSetFromString((String) properties.get(Discovery.DISCOVERED_MEMBERS_PROPERTY_NAME));
+                if (discoveredMemberSet != null && newDiscoveredMemberSet != null && !collectionEquals(discoveredMemberSet, newDiscoveredMemberSet)) {
+                    discoveredMemberSet = newDiscoveredMemberSet;
+                    updated = Boolean.TRUE;
+                }
+            }
+
+            return updated;
+    }
+     /**
+     * Builds a Hazelcast {@link com.hazelcast.config.Config}
+     *
+     * @return
+     */
+    public Config getHazelcastConfig() {
+        System.setProperty("hazelcast.config", xmlConfigLocation);
+        Config config = new XmlConfigBuilder().build();
+        config.setGroupConfig(buildGroupConfig());
+        config.getNetworkConfig().getJoin().setMulticastConfig(buildMulticastConfig());
+        config.getNetworkConfig().getJoin().setTcpIpConfig(buildTcpIpConfig());
+        return config;
+    }
+
+    /**
+     * Builds a {@link com.hazelcast.config.GroupConfig}
+     *
+     * @return
+     */
+    public GroupConfig buildGroupConfig() {
+        GroupConfig groupConfig = new GroupConfig();
+        groupConfig.setName(username);
+        groupConfig.setPassword(password);
+        return groupConfig;
+    }
+
+    /**
+     * Builds a {@link com.hazelcast.config.MulticastConfig}
+     *
+     * @return
+     */
+    public MulticastConfig buildMulticastConfig() {
+        MulticastConfig multicastConfig = new MulticastConfig();
+        multicastConfig.setEnabled(multicastEnabled);
+        multicastConfig.setMulticastPort(multicastPort);
+        multicastConfig.setMulticastGroup(multicastGroup);
+        multicastConfig.setMulticastTimeoutSeconds(multicastTimeoutSeconds);
+        return multicastConfig;
+    }
+
+    /**
+     * Builds a {@link com.hazelcast.config.TcpIpConfig}.
+     *
+     * @return
+     */
+    public TcpIpConfig buildTcpIpConfig() {
+        TcpIpConfig tcpIpConfig = new TcpIpConfig();
+        tcpIpConfig.setEnabled(tcpIpEnabled);
+        tcpIpConfig.setMembers(new ArrayList(tcpIpMemberSet));
+        if(discoveredMemberSet != null && !discoveredMemberSet.isEmpty() && tcpIpConfig.getMembers() != null) {
+            tcpIpConfig.getMembers().addAll(new ArrayList(discoveredMemberSet));
+        }
+        return tcpIpConfig;
+    }
+
+    /**
+     * Converts a comma delimited String to a Set of Strings.
+     *
+     * @param text
+     * @return
+     */
+    private Set<String> createSetFromString(String text) {
+        Set<String> result = new LinkedHashSet<String>();
+        if (text != null) {
+            String[] items = text.split(",");
+            if (items != null && items.length > 0) {
+
+                for (String item : items) {
+                    result.add(item);
+                }
+            }
+        }
+        return result;
+    }
+
+        /**
+     * Returns true if both {@link java.util.Collection}s contain exactly the same items (order doesn't matter).
+     *
+     * @param col1
+     * @param col2
+     * @return
+     */
+    private boolean collectionEquals(Collection col1, Collection col2) {
+        return collectionSubset(col1, col2) && collectionSubset(col2, col1);
+    }
+
+    /**
+     * Returns true if one {@link Collection} contains all items of the others
+     *
+     * @param source
+     * @param target
+     * @return
+     */
+    private boolean collectionSubset(Collection source, Collection target) {
+        if (source == null && target == null) {
+            return true;
+        } else if (source == null || target == null) {
+            return false;
+        } else if (source.isEmpty() && target.isEmpty()) {
+            return true;
+        } else {
+            for (Object item : source) {
+                if (!target.contains(item)) {
+                    return false;
+                }
+            }
+            return true;
+        }
+    }
+}

Modified: karaf/cellar/trunk/hazelcast/src/main/java/org/apache/karaf/cellar/hazelcast/factory/HazelcastServiceFactory.java
URL: http://svn.apache.org/viewvc/karaf/cellar/trunk/hazelcast/src/main/java/org/apache/karaf/cellar/hazelcast/factory/HazelcastServiceFactory.java?rev=1204184&r1=1204183&r2=1204184&view=diff
==============================================================================
--- karaf/cellar/trunk/hazelcast/src/main/java/org/apache/karaf/cellar/hazelcast/factory/HazelcastServiceFactory.java (original)
+++ karaf/cellar/trunk/hazelcast/src/main/java/org/apache/karaf/cellar/hazelcast/factory/HazelcastServiceFactory.java Sun Nov 20 16:50:23 2011
@@ -13,35 +13,16 @@
  */
 package org.apache.karaf.cellar.hazelcast.factory;
 
+import java.util.Map;
+import java.util.concurrent.CountDownLatch;
 import com.hazelcast.config.Config;
-import com.hazelcast.config.GroupConfig;
-import com.hazelcast.config.MulticastConfig;
-import com.hazelcast.config.TcpIpConfig;
-import com.hazelcast.config.XmlConfigBuilder;
 import com.hazelcast.core.Hazelcast;
 import com.hazelcast.core.HazelcastInstance;
-import org.apache.karaf.cellar.core.discovery.Discovery;
-import org.apache.karaf.cellar.core.discovery.DiscoveryTask;
 import org.apache.karaf.cellar.core.utils.CombinedClassLoader;
 import org.osgi.framework.BundleContext;
-import org.osgi.service.cm.Configuration;
-import org.osgi.service.cm.ConfigurationAdmin;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.Dictionary;
-import java.util.Enumeration;
-import java.util.HashMap;
-import java.util.LinkedHashSet;
-import java.util.Map;
-import java.util.Set;
-import java.util.concurrent.Executors;
-import java.util.concurrent.ScheduledExecutorService;
-import java.util.concurrent.TimeUnit;
-
 /**
  * A factory for a Hazelcast Instance, which integration with OSGi Service Registry and Config Admin.
  */
@@ -49,184 +30,35 @@ public class HazelcastServiceFactory  {
 
     private static final transient Logger LOGGER = LoggerFactory.getLogger(HazelcastServiceFactory.class);
 
-    public static final String USERNAME="username";
-    public static final String PASSWORD="password";
-
-
-    public static final String MULTICAST_ENABLED="multicastEnabled";
-    public static final String MULTICAST_GROUP="multicastGroup";
-    public static final String MULTICAST_PORT="multicastPort";
-    public static final String MULTICAST_TIMEOUT_IN_SECONDS="multicastTimeoutSeconds";
-
-    public static final String TCPIP_ENABLED="tcpIpEnabled";
-    public static final String TCPIP_MEMBERS="tcpIpMembers";
-
-    private String username = GroupConfig.DEFAULT_GROUP_NAME;
-    private String password = GroupConfig.DEFAULT_GROUP_PASSWORD;
-
-    private boolean multicastEnabled = MulticastConfig.DEFAULT_ENABLED;
-    private String multicastGroup = MulticastConfig.DEFAULT_MULTICAST_GROUP;
-    private int multicastPort = MulticastConfig.DEFAULT_MULTICAST_PORT;
-    private int multicastTimeoutSeconds = MulticastConfig.DEFAULT_MULTICAST_TIMEOUT_SECONDS;
-
-    private boolean tcpIpEnabled = true;
-    private String tcpIpMembers = "";
-    private Set<String> tcpIpMemberSet = new LinkedHashSet<String>();
-    private Set<String> discoveredMemberSet = new LinkedHashSet<String>();
-
-    private DiscoveryTask discoveryTask;
-    private CombinedClassLoader combinedClassLoader;
-    private ConfigurationAdmin configurationAdmin;
-
     private BundleContext bundleContext;
+    private CombinedClassLoader combinedClassLoader;
+    private HazelcastConfigurationManager configurationManager = new HazelcastConfigurationManager();
 
-    private ScheduledExecutorService scheduler = Executors.newSingleThreadScheduledExecutor();
-
+    private CountDownLatch initializationLatch = new CountDownLatch(1);
+    private CountDownLatch instnaceLatch = new CountDownLatch(1);
     private HazelcastInstance instance;
 
 
     public void init() {
-        if (discoveryTask != null) {
-            scheduler.scheduleAtFixedRate(discoveryTask, 0, 10, TimeUnit.SECONDS);
-        }  else {
-            LOGGER.warn("Did not found a discovery task");
-        }
-        if(combinedClassLoader != null) {
+        if (combinedClassLoader != null) {
             combinedClassLoader.addBundle(bundleContext.getBundle());
         }
-        createInstance();
+        initializationLatch.countDown();
     }
 
     public void destroy() {
-        scheduler.shutdown();
-    }
-
-    /**
-     * Creates or Updates Hazelcast Instance.
-     *
-     * @param properties
-     */
-    public void update(Map properties) {
-            Boolean updated = Boolean.FALSE;
-            //We need it to properly instantiate Hazelcast.
-            if(combinedClassLoader != null) {
-                Thread.currentThread().setContextClassLoader(combinedClassLoader);
-            }
-            if (properties != null) {
-                if (properties.containsKey(USERNAME)) {
-                    String newUsername = (String) properties.get(USERNAME);
-                    if (username != null && newUsername != null && !username.endsWith(newUsername)) {
-                        this.username = newUsername;
-                        updated = Boolean.TRUE;
-                    }
-                }
-
-                if (properties.containsKey(PASSWORD)) {
-                    String newPassword = (String) properties.get(PASSWORD);
-                    if (password != null && !password.equals(newPassword)) {
-                        this.password = newPassword;
-                        updated = Boolean.TRUE;
-                    }
-                }
-
-                Boolean newMulticastEnabled = Boolean.parseBoolean((String) properties.get(MULTICAST_ENABLED));
-                if (multicastEnabled != newMulticastEnabled) {
-                    this.multicastEnabled = newMulticastEnabled;
-                    updated = Boolean.TRUE;
-                }
-
-                if (properties.containsKey(MULTICAST_GROUP)) {
-                    String newMulticastGroup = (String) properties.get(MULTICAST_GROUP);
-                    if (multicastGroup != null && newMulticastGroup != null && !multicastGroup.endsWith(newMulticastGroup)) {
-                        this.multicastGroup = newMulticastGroup;
-                        updated = Boolean.TRUE;
-                    }
-
-                }
-
-                if (properties.containsKey(MULTICAST_PORT)) {
-                    try {
-                        int newMulticastPort = Integer.parseInt((String) properties.get(MULTICAST_PORT));
-                        if (multicastPort != 0 && multicastPort != newMulticastPort) {
-                            this.multicastPort = newMulticastPort;
-                            updated = Boolean.TRUE;
-                        }
-                    } catch (NumberFormatException ex) {
-                        LOGGER.warn("Could not parse port number", ex);
-                    }
-                }
-
-                if (properties.containsKey(MULTICAST_TIMEOUT_IN_SECONDS)) {
-                    try {
-                        int newMulticastTimeoutSeconds = Integer.parseInt((String) properties.get(MULTICAST_TIMEOUT_IN_SECONDS));
-                        if (multicastTimeoutSeconds != 0 && multicastTimeoutSeconds != newMulticastTimeoutSeconds) {
-                            this.multicastTimeoutSeconds = newMulticastTimeoutSeconds;
-                            updated = Boolean.TRUE;
-                        }
-                    } catch (NumberFormatException ex) {
-                        LOGGER.warn("Could not parse multicast timeout in seconds", ex);
-                    }
-                }
-
-                if (properties.containsKey(TCPIP_ENABLED)) {
-                    Boolean newTcpIpEnabled = Boolean.parseBoolean((String) properties.get(TCPIP_ENABLED));
-                    if (tcpIpEnabled != newTcpIpEnabled) {
-                        this.tcpIpEnabled = newTcpIpEnabled;
-                        updated = Boolean.TRUE;
-                    }
-                }
-
-                Set<String> newTcpIpMemberSet = createSetFromString((String) properties.get(TCPIP_MEMBERS));
-                if (tcpIpMemberSet != null && newTcpIpMemberSet != null && !collectionEquals(tcpIpMemberSet, newTcpIpMemberSet)) {
-                    tcpIpMemberSet = newTcpIpMemberSet;
-                    updated = Boolean.TRUE;
-                }
-
-                Set<String> newDiscoveredMemberSet = createSetFromString((String) properties.get(Discovery.DISCOVERED_MEMBERS_PROPERTY_NAME));
-                if (discoveredMemberSet != null && newDiscoveredMemberSet != null && !collectionEquals(discoveredMemberSet, newDiscoveredMemberSet)) {
-                    discoveredMemberSet = newDiscoveredMemberSet;
-                    updated = Boolean.TRUE;
-                }
-            }
-
-            if (updated) {
-                updateMemberList();
-            }
-    }
-
-    public void createInstance() {
-        Configuration configuration = null;
-        Map configurationMap = new HashMap();
-        try {
-            configuration = configurationAdmin.getConfiguration("org.apache.karaf.cellar.instance");
-            Dictionary dictionary = configuration.getProperties();
-            if (dictionary != null && !dictionary.isEmpty()) {
-                Enumeration enumeration = dictionary.keys();
-
-                while (enumeration.hasMoreElements()) {
-                    String key = (String) enumeration.nextElement();
-                    String value = (String) dictionary.get(key);
-                    configurationMap.put(key, value);
-                }
-            }
-            update(configurationMap);
-        } catch (IOException e) {
-           LOGGER.error("Could not read instnace configuration.",e);
+        if (instance != null) {
+            instance.getLifecycleService().shutdown();
         }
-
     }
 
-    public void updateMemberList() {
-        HazelcastInstance instance = getInstance();
-        if (instance != null) {
-            try {
-                instance.getConfig().setGroupConfig(buildGroupConfig());
-                instance.getConfig().getNetworkConfig().getJoin().setMulticastConfig(buildMulticastConfig());
-                instance.getConfig().getNetworkConfig().getJoin().setTcpIpConfig(buildTcpIpConfig());
-                instance.getLifecycleService().restart();
-            } catch (Exception ex) {
-                LOGGER.error("Error while restarting Hazelcast instance.", ex);
-            }
+    public void update(Map properties) throws InterruptedException {
+        if(configurationManager.isUpdated(properties)) {
+            instnaceLatch.await();
+            Config updatedConfig = configurationManager.getHazelcastConfig();
+            instance.getConfig().setNetworkConfig(updatedConfig.getNetworkConfig());
+            instance.getConfig().setGroupConfig(updatedConfig.getGroupConfig());
+            instance.getLifecycleService().restart();
         }
     }
 
@@ -235,9 +67,11 @@ public class HazelcastServiceFactory  {
      *
      * @return
      */
-    public HazelcastInstance getInstance() {
+    public HazelcastInstance getInstance() throws InterruptedException {
         if (instance == null) {
-           this.instance = buildInstance();
+                initializationLatch.await();
+                this.instance = buildInstance();
+                instnaceLatch.countDown();
         }
         return instance;
     }
@@ -251,176 +85,7 @@ public class HazelcastServiceFactory  {
         if(combinedClassLoader != null) {
             Thread.currentThread().setContextClassLoader(combinedClassLoader);
         }
-        return Hazelcast.newHazelcastInstance(buildConfig());
-    }
-
-    /**
-     * Builds a Hazelcast {@link Config}
-     *
-     * @return
-     */
-    public Config buildConfig() {
-        Config config = new XmlConfigBuilder().build();
-        config.setGroupConfig(buildGroupConfig());
-        config.getNetworkConfig().getJoin().setMulticastConfig(buildMulticastConfig());
-        config.getNetworkConfig().getJoin().setTcpIpConfig(buildTcpIpConfig());
-        return config;
-    }
-
-    /**
-     * Builds a {@link GroupConfig}
-     *
-     * @return
-     */
-    public GroupConfig buildGroupConfig() {
-        GroupConfig groupConfig = new GroupConfig();
-        groupConfig.setName(username);
-        groupConfig.setPassword(password);
-        return groupConfig;
-    }
-
-    /**
-     * Builds a {@link MulticastConfig}
-     *
-     * @return
-     */
-    public MulticastConfig buildMulticastConfig() {
-        MulticastConfig multicastConfig = new MulticastConfig();
-        multicastConfig.setEnabled(multicastEnabled);
-        multicastConfig.setMulticastPort(multicastPort);
-        multicastConfig.setMulticastGroup(multicastGroup);
-        multicastConfig.setMulticastTimeoutSeconds(multicastTimeoutSeconds);
-        return multicastConfig;
-    }
-
-    /**
-     * Builds a {@link TcpIpConfig}.
-     *
-     * @return
-     */
-    public TcpIpConfig buildTcpIpConfig() {
-        TcpIpConfig tcpIpConfig = new TcpIpConfig();
-        tcpIpConfig.setEnabled(tcpIpEnabled);
-        tcpIpConfig.setMembers(new ArrayList(tcpIpMemberSet));
-        if(discoveredMemberSet != null && !discoveredMemberSet.isEmpty() && tcpIpConfig.getMembers() != null) {
-            tcpIpConfig.getMembers().addAll(new ArrayList(discoveredMemberSet));
-        }
-        return tcpIpConfig;
-    }
-
-    /**
-     * Converts a comma delimited String to a Set of Strings.
-     *
-     * @param text
-     * @return
-     */
-    private Set<String> createSetFromString(String text) {
-        Set<String> result = new LinkedHashSet<String>();
-        if (text != null) {
-            String[] items = text.split(",");
-            if (items != null && items.length > 0) {
-
-                for (String item : items) {
-                    result.add(item);
-                }
-            }
-        }
-        return result;
-    }
-
-    /**
-     * Returns true if both {@link Collection}s contain exactly the same items (order doesn't matter).
-     *
-     * @param col1
-     * @param col2
-     * @return
-     */
-    private boolean collectionEquals(Collection col1, Collection col2) {
-        return collectionSubset(col1, col2) && collectionSubset(col2, col1);
-    }
-
-    /**
-     * Returns true if one {@link Collection} contains all items of the others
-     *
-     * @param source
-     * @param target
-     * @return
-     */
-    private boolean collectionSubset(Collection source, Collection target) {
-        if (source == null && target == null) {
-            return true;
-        } else if (source == null || target == null) {
-            return false;
-        } else if (source.isEmpty() && target.isEmpty()) {
-            return true;
-        } else {
-            for (Object item : source) {
-                if (!target.contains(item)) {
-                    return false;
-                }
-            }
-            return true;
-        }
-    }
-
-    public String getUsername() {
-        return username;
-    }
-
-    public void setUsername(String username) {
-        if (username != null) {
-            this.username = username;
-        }
-    }
-
-    public String getPassword() {
-        return password;
-    }
-
-    public void setPassword(String password) {
-        if (password != null) {
-            this.password = password;
-        }
-    }
-
-    public boolean isMulticastEnabled() {
-        return multicastEnabled;
-    }
-
-    public void setMulticastEnabled(boolean multicastEnabled) {
-        this.multicastEnabled = multicastEnabled;
-    }
-
-    public String getMulticastGroup() {
-        return multicastGroup;
-    }
-
-    public void setMulticastGroup(String multicastGroup) {
-        this.multicastGroup = multicastGroup;
-    }
-
-    public int getMulticastPort() {
-        return multicastPort;
-    }
-
-    public void setMulticastPort(int multicastPort) {
-        this.multicastPort = multicastPort;
-    }
-
-    public boolean isTcpIpEnabled() {
-        return tcpIpEnabled;
-    }
-
-    public void setTcpIpEnabled(boolean tcpIpEnabled) {
-        this.tcpIpEnabled = tcpIpEnabled;
-    }
-
-    public String getTcpIpMembers() {
-        return tcpIpMembers;
-    }
-
-    public void setTcpIpMembers(String tcpIpMembers) {
-        this.tcpIpMembers = tcpIpMembers;
+        return Hazelcast.newHazelcastInstance(configurationManager.getHazelcastConfig());
     }
 
     public BundleContext getBundleContext() {
@@ -431,14 +96,6 @@ public class HazelcastServiceFactory  {
         this.bundleContext = bundleContext;
     }
 
-    public DiscoveryTask getDiscoveryTask() {
-        return discoveryTask;
-    }
-
-    public void setDiscoveryTask(DiscoveryTask discoveryTask) {
-        this.discoveryTask = discoveryTask;
-    }
-
     public CombinedClassLoader getCombinedClassLoader() {
         return combinedClassLoader;
     }
@@ -446,12 +103,4 @@ public class HazelcastServiceFactory  {
     public void setCombinedClassLoader(CombinedClassLoader combinedClassLoader) {
         this.combinedClassLoader = combinedClassLoader;
     }
-
-    public ConfigurationAdmin getConfigurationAdmin() {
-        return configurationAdmin;
-    }
-
-    public void setConfigurationAdmin(ConfigurationAdmin configurationAdmin) {
-        this.configurationAdmin = configurationAdmin;
-    }
 }

Modified: karaf/cellar/trunk/hazelcast/src/main/resources/OSGI-INF/blueprint/blueprint.xml
URL: http://svn.apache.org/viewvc/karaf/cellar/trunk/hazelcast/src/main/resources/OSGI-INF/blueprint/blueprint.xml?rev=1204184&r1=1204183&r2=1204184&view=diff
==============================================================================
--- karaf/cellar/trunk/hazelcast/src/main/resources/OSGI-INF/blueprint/blueprint.xml (original)
+++ karaf/cellar/trunk/hazelcast/src/main/resources/OSGI-INF/blueprint/blueprint.xml Sun Nov 20 16:50:23 2011
@@ -22,19 +22,16 @@
     <bean id="hazelcast" class="com.hazelcast.core.Hazelcast" factory-ref="instanceFactory"
           factory-method="getInstance" destroy-method="shutdown"/>
 
-
     <bean id="instanceFactory" class="org.apache.karaf.cellar.hazelcast.factory.HazelcastServiceFactory"
           init-method="init" destroy-method="destroy">
-        <property name="discoveryTask" ref="discoveryTask"/>
         <property name="combinedClassLoader" ref="combinedClassLoader"/>
         <property name="bundleContext" ref="blueprintBundleContext"/>
-        <property name="configurationAdmin" ref="configurationAdmin"/>
         <cm:managed-properties persistent-id="org.apache.karaf.cellar.instance" update-strategy="component-managed"
                                   update-method="update"/>
     </bean>
 
     <!-- Discovery Task -->
-    <bean id="discoveryTask" class="org.apache.karaf.cellar.core.discovery.DiscoveryTask">
+    <bean id="discoveryTask" class="org.apache.karaf.cellar.core.discovery.DiscoveryTask" init-method="init" destroy-method="destroy">
         <property name="discoveryServices" ref="discoveryServices"/>
         <property name="configurationAdmin" ref="configurationAdmin"/>
     </bean>

Modified: karaf/cellar/trunk/hazelcast/src/test/java/org/apache/karaf/cellar/hazelcast/factory/HazelcastServiceFactoryTest.java
URL: http://svn.apache.org/viewvc/karaf/cellar/trunk/hazelcast/src/test/java/org/apache/karaf/cellar/hazelcast/factory/HazelcastServiceFactoryTest.java?rev=1204184&r1=1204183&r2=1204184&view=diff
==============================================================================
--- karaf/cellar/trunk/hazelcast/src/test/java/org/apache/karaf/cellar/hazelcast/factory/HazelcastServiceFactoryTest.java (original)
+++ karaf/cellar/trunk/hazelcast/src/test/java/org/apache/karaf/cellar/hazelcast/factory/HazelcastServiceFactoryTest.java Sun Nov 20 16:50:23 2011
@@ -38,8 +38,8 @@ public class HazelcastServiceFactoryTest
     @Test
     public void testDefaultInstance() throws InterruptedException {
         HazelcastServiceFactory factory = new HazelcastServiceFactory();
-        factory.setUsername(GroupConfig.DEFAULT_GROUP_NAME);
-        factory.setPassword(GroupConfig.DEFAULT_GROUP_PASSWORD);
+        factory.init();
+        factory.getInstance();
         factory.update(null);
         HazelcastInstance defaultInstance = Hazelcast.newHazelcastInstance(null);
         HazelcastInstance factoryInstance = factory.getInstance();