Added zip packaging for distributed configuration publisher

Project: http://git-wip-us.apache.org/repos/asf/oodt/repo
Commit: http://git-wip-us.apache.org/repos/asf/oodt/commit/27a28daa
Tree: http://git-wip-us.apache.org/repos/asf/oodt/tree/27a28daa
Diff: http://git-wip-us.apache.org/repos/asf/oodt/diff/27a28daa

Branch: refs/heads/feature/zookeeper-config
Commit: 27a28daa3d3c448b462bd9a33eb6ac4fd859b75a
Parents: 5fcf222
Author: Imesha Sudasingha <[email protected]>
Authored: Sun Jul 2 20:53:49 2017 +0530
Committer: Imesha Sudasingha <[email protected]>
Committed: Sun Jul 2 20:53:49 2017 +0530

----------------------------------------------------------------------
 config/pom.xml                                  |   36 +-
 config/src/main/assembly/assembly.xml           |   56 +
 .../java/org/apache/oodt/config/Constants.java  |    7 +
 .../DistributedConfigurationManager.java        |    1 -
 .../DistributedConfigurationPublisher.java      |  208 -
 .../config/distributed/cli/CmdLineOptions.java  |   57 +
 .../cli/DistributedConfigurationPublisher.java  |  300 ++
 .../config/distributed/utils/CuratorUtils.java  |    1 +
 .../src/main/resources/etc/config-publisher.xml |   36 +
 config/src/main/resources/etc/log4j.xml         |   34 +
 .../main/resources/examples/filemgr.properties  |  114 +
 .../src/main/resources/examples/mime-types.xml  | 4119 ++++++++++++++++++
 .../DistributedConfigurationPublisherTest.java  |   54 +-
 .../oodt/config/distributed/TestServer.java     |   45 +
 .../resources/distributed-config-publisher.xml  |   56 -
 .../src/test/resources/etc/config-publisher.xml |   50 +
 config/src/test/resources/filemgr.properties    |  114 -
 config/src/test/resources/log4j.xml             |   34 -
 config/src/test/resources/mime-types.xml        | 4119 ------------------
 core/pom.xml                                    |    6 +
 20 files changed, 4862 insertions(+), 4585 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/oodt/blob/27a28daa/config/pom.xml
----------------------------------------------------------------------
diff --git a/config/pom.xml b/config/pom.xml
index 891f520..d75e032 100644
--- a/config/pom.xml
+++ b/config/pom.xml
@@ -16,50 +16,68 @@
     <description>OODT project for distributed configuration management 
support</description>
 
     <dependencies>
-
         <dependency>
             <groupId>org.apache.curator</groupId>
             <artifactId>curator-framework</artifactId>
         </dependency>
-
         <dependency>
             <groupId>commons-io</groupId>
             <artifactId>commons-io</artifactId>
         </dependency>
-
         <dependency>
             <groupId>org.springframework</groupId>
             <artifactId>spring-beans</artifactId>
         </dependency>
-
         <dependency>
             <groupId>org.springframework</groupId>
             <artifactId>spring-context</artifactId>
         </dependency>
-
         <dependency>
             <groupId>org.springframework</groupId>
             <artifactId>spring-core</artifactId>
         </dependency>
-
+        <dependency>
+            <groupId>args4j</groupId>
+            <artifactId>args4j</artifactId>
+        </dependency>
         <dependency>
             <groupId>org.slf4j</groupId>
             <artifactId>slf4j-api</artifactId>
         </dependency>
-
         <dependency>
             <groupId>org.slf4j</groupId>
             <artifactId>slf4j-log4j12</artifactId>
         </dependency>
-
         <dependency>
             <groupId>junit</groupId>
             <artifactId>junit</artifactId>
         </dependency>
-
         <dependency>
             <groupId>org.apache.curator</groupId>
             <artifactId>curator-test</artifactId>
         </dependency>
     </dependencies>
+
+    <build>
+        <plugins>
+            <plugin>
+                <groupId>org.apache.maven.plugins</groupId>
+                <artifactId>maven-assembly-plugin</artifactId>
+                <version>2.2-beta-2</version>
+                <configuration>
+                    <descriptors>
+                        <descriptor>src/main/assembly/assembly.xml</descriptor>
+                    </descriptors>
+                </configuration>
+                <executions>
+                    <execution>
+                        <goals>
+                            <goal>single</goal>
+                        </goals>
+                        <phase>package</phase>
+                    </execution>
+                </executions>
+            </plugin>
+        </plugins>
+    </build>
 </project>
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/oodt/blob/27a28daa/config/src/main/assembly/assembly.xml
----------------------------------------------------------------------
diff --git a/config/src/main/assembly/assembly.xml 
b/config/src/main/assembly/assembly.xml
new file mode 100644
index 0000000..2743cab
--- /dev/null
+++ b/config/src/main/assembly/assembly.xml
@@ -0,0 +1,56 @@
+<!--
+  ~ 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.
+  -->
+<assembly>
+    <id>dist</id>
+    <formats>
+        <format>tar.gz</format>
+        <format>zip</format>
+    </formats>
+    <includeBaseDirectory>true</includeBaseDirectory>
+    <baseDirectory>${project.artifactId}-${project.version}</baseDirectory>
+    <includeSiteDirectory>false</includeSiteDirectory>
+    <fileSets>
+        <fileSet>
+            <directory>${basedir}</directory>
+            <outputDirectory>.</outputDirectory>
+            <includes>
+                <include>LICENSE.txt</include>
+                <include>CHANGES.txt</include>
+            </includes>
+        </fileSet>
+        <fileSet>
+            <directory>${basedir}/src/main/bin</directory>
+            <outputDirectory>bin</outputDirectory>
+            <includes/>
+            <fileMode>755</fileMode>
+        </fileSet>
+        <fileSet>
+            <directory>${basedir}/src/main/resources</directory>
+            <outputDirectory>.</outputDirectory>
+            <includes/>
+        </fileSet>
+    </fileSets>
+    <dependencySets>
+        <dependencySet>
+            <outputDirectory>lib</outputDirectory>
+            <unpack>false</unpack>
+            <useProjectArtifact>true</useProjectArtifact>
+            <useTransitiveDependencies>true</useTransitiveDependencies>
+            <unpackOptions/>
+        </dependencySet>
+    </dependencySets>
+</assembly>

http://git-wip-us.apache.org/repos/asf/oodt/blob/27a28daa/config/src/main/java/org/apache/oodt/config/Constants.java
----------------------------------------------------------------------
diff --git a/config/src/main/java/org/apache/oodt/config/Constants.java 
b/config/src/main/java/org/apache/oodt/config/Constants.java
index 033101b..d6969fe 100644
--- a/config/src/main/java/org/apache/oodt/config/Constants.java
+++ b/config/src/main/java/org/apache/oodt/config/Constants.java
@@ -17,6 +17,8 @@
 
 package org.apache.oodt.config;
 
+import java.io.File;
+
 /**
  * Constants to be used by the config package
  *
@@ -27,12 +29,17 @@ public class Constants {
     private Constants() {
     }
 
+    public static final String SEPARATOR = File.separator;
+
     /** Node name to be used when the configuration manager is the standalone 
version */
     public static final String STANDALONE_NODE_NAME = "local";
 
     /** Default environment name to be used */
     public static final String DEFAULT_ENVIRONMENT = "default";
 
+    /** The XML file name in which the configuration to be published to 
zookeeper is defined */
+    public static final String CONFIG_PUBLISHER_XML = "etc" + SEPARATOR + 
"config-publisher.xml";
+
     public static class Properties {
         /** The system property to be set in order to enable distributed 
configuration management */
         public static final String ENABLE_DISTRIBUTED_CONFIGURATION = 
"org.apache.oodt.config.distributed";

http://git-wip-us.apache.org/repos/asf/oodt/blob/27a28daa/config/src/main/java/org/apache/oodt/config/distributed/DistributedConfigurationManager.java
----------------------------------------------------------------------
diff --git 
a/config/src/main/java/org/apache/oodt/config/distributed/DistributedConfigurationManager.java
 
b/config/src/main/java/org/apache/oodt/config/distributed/DistributedConfigurationManager.java
index d16df7e..1a3f390 100644
--- 
a/config/src/main/java/org/apache/oodt/config/distributed/DistributedConfigurationManager.java
+++ 
b/config/src/main/java/org/apache/oodt/config/distributed/DistributedConfigurationManager.java
@@ -114,7 +114,6 @@ public class DistributedConfigurationManager extends 
ConfigurationManager {
         logger.debug("Saving configuration files for : {}", componentName);
         saveConfigFiles();
         logger.info("Configuration files saved for : {}", componentName);
-
     }
 
     /**

http://git-wip-us.apache.org/repos/asf/oodt/blob/27a28daa/config/src/main/java/org/apache/oodt/config/distributed/DistributedConfigurationPublisher.java
----------------------------------------------------------------------
diff --git 
a/config/src/main/java/org/apache/oodt/config/distributed/DistributedConfigurationPublisher.java
 
b/config/src/main/java/org/apache/oodt/config/distributed/DistributedConfigurationPublisher.java
deleted file mode 100644
index 37b57c9..0000000
--- 
a/config/src/main/java/org/apache/oodt/config/distributed/DistributedConfigurationPublisher.java
+++ /dev/null
@@ -1,208 +0,0 @@
-/*
- * 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.oodt.config.distributed;
-
-import org.apache.commons.io.FileUtils;
-import org.apache.curator.framework.CuratorFramework;
-import org.apache.oodt.config.Constants;
-import org.apache.oodt.config.distributed.utils.CuratorUtils;
-import org.apache.zookeeper.data.Stat;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-import org.springframework.beans.BeansException;
-import org.springframework.context.ApplicationContext;
-import org.springframework.context.support.ClassPathXmlApplicationContext;
-
-import java.io.File;
-import java.io.IOException;
-import java.net.URISyntaxException;
-import java.net.URL;
-import java.util.Map;
-import java.util.concurrent.TimeUnit;
-
-import static org.apache.oodt.config.Constants.Properties.ZK_CONNECT_STRING;
-import static org.apache.oodt.config.Constants.Properties.ZK_PROPERTIES_FILE;
-
-/**
- * The class to publish configuration to Zookeeper. When using distributed 
configuration with OODT, configuration per
- * each component type needs to be stored in zookeeper beforehand. This class, 
provides the means to do that.
- *
- * @author Imesha Sudasingha
- */
-public class DistributedConfigurationPublisher {
-
-    private static final Logger logger = 
LoggerFactory.getLogger(DistributedConfigurationPublisher.class);
-
-    private Map<String, String> propertiesFiles;
-    private Map<String, String> configFiles;
-    private String connectString;
-    private CuratorFramework client;
-    private ZNodePaths zNodePaths;
-    private String componentName;
-
-    public DistributedConfigurationPublisher(String componentName) {
-        this.componentName = componentName;
-        this.zNodePaths = new ZNodePaths(componentName);
-
-        if (System.getProperty(ZK_PROPERTIES_FILE) == null && 
System.getProperty(Constants.Properties.ZK_CONNECT_STRING) == null) {
-            throw new IllegalArgumentException("Zookeeper requires system 
properties " + ZK_PROPERTIES_FILE + " or " + ZK_CONNECT_STRING + " to be set");
-        }
-
-        if (System.getProperty(ZK_PROPERTIES_FILE) != null) {
-            try {
-                CuratorUtils.loadZookeeperProperties();
-            } catch (IOException e) {
-                logger.error("Error occurred when loading properties from 
properties file");
-            }
-        }
-
-        if (System.getProperty(Constants.Properties.ZK_CONNECT_STRING) == 
null) {
-            throw new IllegalArgumentException("Zookeeper requires a proper 
connect string to connect to zookeeper ensemble");
-        }
-
-        connectString = 
System.getProperty(Constants.Properties.ZK_CONNECT_STRING);
-        logger.info("Using zookeeper connect string : {}", connectString);
-
-        startZookeeper();
-    }
-
-    /**
-     * Creates a {@link CuratorFramework} instance and start it. This method 
will wait a maximum amount of
-     * {@link Constants.Properties#ZK_STARTUP_TIMEOUT} milli-seconds until the 
client connects to the zookeeper ensemble.
-     */
-    private void startZookeeper() {
-        client = CuratorUtils.getCuratorFrameworkClient(connectString, logger);
-
-        client.start();
-        logger.info("Curator framework start operation invoked");
-
-        int startupTimeOutMs = 
Integer.parseInt(System.getProperty(Constants.Properties.ZK_STARTUP_TIMEOUT, 
"30000"));
-        try {
-            logger.info("Waiting to connect to zookeeper, startupTimeout : 
{}", startupTimeOutMs);
-            client.blockUntilConnected(startupTimeOutMs, 
TimeUnit.MILLISECONDS);
-        } catch (InterruptedException ex) {
-            logger.error("Interrupted while waiting to connect zookeeper 
(connectString : {}) : {}", ex, connectString);
-        }
-
-        if (!client.getZookeeperClient().isConnected()) {
-            throw new IllegalStateException("Could not connect to ZooKeeper : 
" + connectString);
-        }
-
-        logger.info("CuratorFramework client started successfully");
-    }
-
-    public void publishConfiguration() throws Exception {
-        logger.debug("Publishing properties files : {}", propertiesFiles);
-        publishConfiguration(propertiesFiles, true);
-        logger.info("Properties files published successfully");
-
-        logger.debug("Publishing config files : {}", configFiles);
-        publishConfiguration(configFiles, false);
-        logger.info("Config files published successfully");
-
-        // TODO: 6/17/17 Verify whether the given configuration are published 
correctly
-    }
-
-    private void publishConfiguration(Map<String, String> fileMapping, boolean 
isProperties) throws Exception {
-        for (Map.Entry<String, String> entry : fileMapping.entrySet()) {
-            logger.debug("Publishing configuration {} - {}", entry.getKey(), 
entry.getValue());
-            URL resource = 
Thread.currentThread().getContextClassLoader().getResource(entry.getKey());
-
-            String content;
-            try {
-                content = FileUtils.readFileToString(new 
File(resource.toURI()));
-            } catch (IOException | URISyntaxException e) {
-                logger.error("Unable to read file : {}", entry.getKey(), e);
-                continue;
-            }
-
-            String zNodePath = isProperties ? 
zNodePaths.getPropertiesZNodePath(entry.getValue()) : 
zNodePaths.getConfigurationZNodePath(entry.getValue());
-            if (client.checkExists().forPath(zNodePath) != null) {
-                byte[] bytes = client.getData().forPath(zNodePath);
-                String existingData = new String(bytes);
-                if (content.equals(existingData)) {
-                    logger.warn("{} already exists in zookeeper at {}", 
entry.getKey(), entry.getValue());
-                } else {
-                    Stat stat = client.setData().forPath(zNodePath, 
content.getBytes());
-                    if (stat != null) {
-                        logger.info("Published configuration file {} to {}", 
entry.getKey(), entry.getValue());
-                    }
-                }
-            } else {
-                /*
-                 * Creating these ZNodes with parent 'Containers' is important 
since containers are automatically deleted
-                 * when no child node is present under them.
-                 */
-                
client.create().creatingParentContainersIfNeeded().forPath(zNodePath, 
content.getBytes());
-            }
-        }
-    }
-
-    public Map<String, String> getPropertiesFiles() {
-        return propertiesFiles;
-    }
-
-    public void setPropertiesFiles(Map<String, String> propertiesFiles) {
-        this.propertiesFiles = propertiesFiles;
-    }
-
-    public Map<String, String> getConfigFiles() {
-        return configFiles;
-    }
-
-    public void setConfigFiles(Map<String, String> configFiles) {
-        this.configFiles = configFiles;
-    }
-
-    public ZNodePaths getZNodePaths() {
-        return zNodePaths;
-    }
-
-    public static void main(String[] args) {
-        if (args.length < 1) {
-            logger.error("Spring configuration file needs to be given as an 
argument");
-            return;
-        }
-
-        logger.info("Starting publishing configuration. Spring conf : {}", 
args[0]);
-
-        try {
-            ApplicationContext applicationContext = new 
ClassPathXmlApplicationContext(args[0]);
-            Map distributedConfigurationPublisher = 
applicationContext.getBeansOfType(DistributedConfigurationPublisher.class);
-            for (Object bean : distributedConfigurationPublisher.values()) {
-                DistributedConfigurationPublisher publisher = 
(DistributedConfigurationPublisher) bean;
-
-                logger.debug("Publishing configuration for : {}", 
publisher.getComponentName());
-                publisher.publishConfiguration();
-                logger.info("Published configuration for : {}", 
publisher.getComponentName());
-            }
-        } catch (BeansException e) {
-            logger.error("Error occurred when obtaining configuration 
publisher beans", e);
-            return;
-        } catch (Exception e) {
-            logger.error("Error occurred when publishing configuration to 
zookeeper", e);
-            return;
-        }
-
-        logger.info("Published configuration successfully");
-    }
-
-    public String getComponentName() {
-        return componentName;
-    }
-}

http://git-wip-us.apache.org/repos/asf/oodt/blob/27a28daa/config/src/main/java/org/apache/oodt/config/distributed/cli/CmdLineOptions.java
----------------------------------------------------------------------
diff --git 
a/config/src/main/java/org/apache/oodt/config/distributed/cli/CmdLineOptions.java
 
b/config/src/main/java/org/apache/oodt/config/distributed/cli/CmdLineOptions.java
new file mode 100644
index 0000000..afa6350
--- /dev/null
+++ 
b/config/src/main/java/org/apache/oodt/config/distributed/cli/CmdLineOptions.java
@@ -0,0 +1,57 @@
+/*
+ * 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.oodt.config.distributed.cli;
+
+import org.kohsuke.args4j.Option;
+
+/**
+ * Bean class used to map CLI options and arguments provided by the user when 
publishing configuration to zookeeper
+ *
+ * @author Imesha Sudaingha
+ */
+public class CmdLineOptions {
+
+    @Option(name = "-connectString", usage = "Zookeeper connect string", 
required = true)
+    private String connectString;
+
+    @Option(name = "-publish", usage = "Publishes configuration specified in 
the spring config file to zookeeper. " +
+            "Any current similar config in zookeeper will be overwritten. If 
not specified, command will be assumed as a publish")
+    private boolean publish = true;
+
+    @Option(name = "-verify", usage = "Verifies the content in the local files 
and the published ones. Results will be printed.")
+    private boolean verify = true;
+
+    @Option(name = "-clear", usage = "Unpublish any configuration which has 
been published earlier using the same spring config file")
+    private boolean clear = false;
+
+    public String getConnectString() {
+        return connectString;
+    }
+
+    public boolean isPublish() {
+        return publish;
+    }
+
+    public boolean isVerify() {
+        return verify;
+    }
+
+    public boolean isClear() {
+        return clear;
+    }
+}

http://git-wip-us.apache.org/repos/asf/oodt/blob/27a28daa/config/src/main/java/org/apache/oodt/config/distributed/cli/DistributedConfigurationPublisher.java
----------------------------------------------------------------------
diff --git 
a/config/src/main/java/org/apache/oodt/config/distributed/cli/DistributedConfigurationPublisher.java
 
b/config/src/main/java/org/apache/oodt/config/distributed/cli/DistributedConfigurationPublisher.java
new file mode 100644
index 0000000..03cdfc7
--- /dev/null
+++ 
b/config/src/main/java/org/apache/oodt/config/distributed/cli/DistributedConfigurationPublisher.java
@@ -0,0 +1,300 @@
+/*
+ * 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.oodt.config.distributed.cli;
+
+import org.apache.commons.io.FileUtils;
+import org.apache.curator.framework.CuratorFramework;
+import org.apache.oodt.config.Constants;
+import org.apache.oodt.config.distributed.ZNodePaths;
+import org.apache.oodt.config.distributed.utils.CuratorUtils;
+import org.apache.zookeeper.data.Stat;
+import org.kohsuke.args4j.CmdLineException;
+import org.kohsuke.args4j.CmdLineParser;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.springframework.beans.BeansException;
+import org.springframework.context.ApplicationContext;
+import org.springframework.context.support.ClassPathXmlApplicationContext;
+
+import java.io.File;
+import java.io.IOException;
+import java.util.Map;
+import java.util.concurrent.TimeUnit;
+
+import static org.apache.oodt.config.Constants.Properties.ZK_CONNECT_STRING;
+import static org.apache.oodt.config.Constants.Properties.ZK_PROPERTIES_FILE;
+
+/**
+ * The class to publish configuration to Zookeeper. When using distributed 
configuration with OODT, configuration per
+ * each component type needs to be stored in zookeeper beforehand. This class, 
provides the means to do that.
+ *
+ * @author Imesha Sudasingha
+ */
+public class DistributedConfigurationPublisher {
+
+    private static final Logger logger = 
LoggerFactory.getLogger(DistributedConfigurationPublisher.class);
+
+    private Map<String, String> propertiesFiles;
+    private Map<String, String> configFiles;
+    private String connectString;
+    private CuratorFramework client;
+    private ZNodePaths zNodePaths;
+    private String componentName;
+
+    public DistributedConfigurationPublisher(String componentName) {
+        this.componentName = componentName;
+        this.zNodePaths = new ZNodePaths(componentName);
+
+        if (System.getProperty(ZK_PROPERTIES_FILE) == null && 
System.getProperty(ZK_CONNECT_STRING) == null) {
+            throw new IllegalArgumentException("Zookeeper requires system 
properties " + ZK_PROPERTIES_FILE + " or " + ZK_CONNECT_STRING + " to be set");
+        }
+
+        if (System.getProperty(ZK_PROPERTIES_FILE) != null) {
+            try {
+                CuratorUtils.loadZookeeperProperties();
+            } catch (IOException e) {
+                logger.error("Error occurred when loading properties from 
properties file");
+            }
+        }
+
+        if (System.getProperty(ZK_CONNECT_STRING) == null) {
+            throw new IllegalArgumentException("Zookeeper requires a proper 
connect string to connect to zookeeper ensemble");
+        }
+
+        connectString = System.getProperty(ZK_CONNECT_STRING);
+        logger.info("Using zookeeper connect string : {}", connectString);
+
+        startZookeeper();
+    }
+
+    /**
+     * Creates a {@link CuratorFramework} instance and start it. This method 
will wait a maximum amount of
+     * {@link Constants.Properties#ZK_STARTUP_TIMEOUT} milli-seconds until the 
client connects to the zookeeper ensemble.
+     */
+    private void startZookeeper() {
+        client = CuratorUtils.getCuratorFrameworkClient(connectString, logger);
+
+        client.start();
+        logger.info("Curator framework start operation invoked");
+
+        int startupTimeOutMs = 
Integer.parseInt(System.getProperty(Constants.Properties.ZK_STARTUP_TIMEOUT, 
"30000"));
+        try {
+            logger.info("Waiting to connect to zookeeper, startupTimeout : 
{}", startupTimeOutMs);
+            client.blockUntilConnected(startupTimeOutMs, 
TimeUnit.MILLISECONDS);
+        } catch (InterruptedException ex) {
+            logger.error("Interrupted while waiting to connect zookeeper 
(connectString : {}) : {}", ex, connectString);
+        }
+
+        if (!client.getZookeeperClient().isConnected()) {
+            throw new IllegalStateException("Could not connect to ZooKeeper : 
" + connectString);
+        }
+
+        logger.info("CuratorFramework client started successfully");
+    }
+
+    /**
+     * Publishes the configuration files specified to zookeeper. If an 
exception is thrown while configuration being
+     * published, no further publishing attempts will be carried on. Error 
will be reported to user.
+     *
+     * @throws Exception Zookeeper errors
+     */
+    public void publishConfiguration() throws Exception {
+        logger.debug("Publishing properties files : {}", propertiesFiles);
+        publishConfiguration(propertiesFiles, true);
+        logger.info("Properties files published successfully");
+
+        logger.debug("Publishing config files : {}", configFiles);
+        publishConfiguration(configFiles, false);
+        logger.info("Config files published successfully");
+    }
+
+    /**
+     * Verified whether the actual content of the local files specified to be 
published are 100% similar to the ones that
+     * has been published and stored in zookeeper at the moment.
+     *
+     * @return true | if content are up to date and similar
+     */
+    public boolean verifyPublishedConfiguration() {
+        try {
+            return verifyPublishedConfiguration(propertiesFiles, true) && 
verifyPublishedConfiguration(configFiles, false);
+        } catch (Exception e) {
+            logger.error("Error occurred when checking published config", e);
+            return false;
+        }
+    }
+
+    private void publishConfiguration(Map<String, String> fileMapping, boolean 
isProperties) throws Exception {
+        for (Map.Entry<String, String> entry : fileMapping.entrySet()) {
+            String filePath = entry.getKey();
+            String relativeZNodePath = entry.getValue();
+            logger.info("Publishing configuration {} - {}", filePath, 
relativeZNodePath);
+
+            String content = getFileContent(filePath);
+
+            String zNodePath = isProperties ? 
zNodePaths.getPropertiesZNodePath(relativeZNodePath) : 
zNodePaths.getConfigurationZNodePath(relativeZNodePath);
+            if (client.checkExists().forPath(zNodePath) != null) {
+                byte[] bytes = client.getData().forPath(zNodePath);
+                String existingData = new String(bytes);
+                if (content.equals(existingData)) {
+                    logger.warn("{} already exists in zookeeper at {}", 
filePath, relativeZNodePath);
+                } else {
+                    Stat stat = client.setData().forPath(zNodePath, 
content.getBytes());
+                    if (stat != null) {
+                        logger.info("Published configuration file {} to {}", 
filePath, relativeZNodePath);
+                    } else {
+                        logger.warn("Unable to publish configuration file {} 
to {}", filePath, relativeZNodePath);
+                    }
+                }
+            } else {
+                /*
+                 * Creating these ZNodes with parent 'Containers' is important 
since containers are automatically deleted
+                 * when no child node is present under them.
+                 */
+                
client.create().creatingParentContainersIfNeeded().forPath(zNodePath, 
content.getBytes());
+                logger.info("Replaced old published configuration at {} with 
content of file : {}", relativeZNodePath, filePath);
+            }
+        }
+    }
+
+    private boolean verifyPublishedConfiguration(Map<String, String> 
fileMapping, boolean isProperties) throws Exception {
+        boolean noError = true;
+        for (Map.Entry<String, String> entry : fileMapping.entrySet()) {
+            String filePath = entry.getKey();
+            String relativeZNodePath = entry.getValue();
+            logger.info("Checking published configuration for {} - {}", 
filePath, relativeZNodePath);
+
+            String originalContent = getFileContent(filePath);
+
+            String zNodePath = isProperties ? 
zNodePaths.getPropertiesZNodePath(relativeZNodePath) : 
zNodePaths.getConfigurationZNodePath(relativeZNodePath);
+            if (client.checkExists().forPath(zNodePath) == null) {
+                logger.error("File : {} hasn't been published to ZNode : {}", 
filePath, relativeZNodePath);
+                noError = false;
+                continue;
+            }
+
+            String publishedContent = new 
String(client.getData().forPath(zNodePath));
+            if (!publishedContent.equals(originalContent)) {
+                logger.error("Content of local file : {} and content published 
to {} are not similar", filePath, relativeZNodePath);
+                noError = false;
+                continue;
+            }
+
+            logger.info("{} - {} configuration checked and OK", filePath, 
relativeZNodePath);
+        }
+
+        return noError;
+    }
+
+    private String getFileContent(String file) {
+        String content;
+        try {
+            content = FileUtils.readFileToString(new File(file));
+        } catch (IOException e) {
+            logger.error("Unable to read file : {}", file, e);
+            throw new IllegalArgumentException("Unable to read content of the 
file : " + file);
+        }
+
+        return content;
+    }
+
+    public Map<String, String> getPropertiesFiles() {
+        return propertiesFiles;
+    }
+
+    public void setPropertiesFiles(Map<String, String> propertiesFiles) {
+        this.propertiesFiles = propertiesFiles;
+    }
+
+    public Map<String, String> getConfigFiles() {
+        return configFiles;
+    }
+
+    public void setConfigFiles(Map<String, String> configFiles) {
+        this.configFiles = configFiles;
+    }
+
+    public ZNodePaths getZNodePaths() {
+        return zNodePaths;
+    }
+
+    public static void main(String[] args) throws Exception {
+        CmdLineOptions cmdLineOptions = new CmdLineOptions();
+        CmdLineParser parser = new CmdLineParser(cmdLineOptions);
+
+        try {
+            parser.parseArgument(args);
+        } catch (CmdLineException e) {
+            System.err.println("There's an error in your command");
+            parser.printUsage(System.err);
+            return;
+        }
+
+        if (cmdLineOptions.getConnectString() == null && 
System.getProperty(ZK_CONNECT_STRING) == null) {
+            System.err.println("Zookeeper connect string is not found");
+            parser.printUsage(System.err);
+            return;
+        } else {
+            System.setProperty(ZK_CONNECT_STRING, 
cmdLineOptions.getConnectString());
+        }
+
+        System.out.println("Starting configuration publishing");
+
+        try {
+            ApplicationContext applicationContext = new 
ClassPathXmlApplicationContext(Constants.CONFIG_PUBLISHER_XML);
+            Map distributedConfigurationPublisher = 
applicationContext.getBeansOfType(DistributedConfigurationPublisher.class);
+
+            for (Object bean : distributedConfigurationPublisher.values()) {
+                DistributedConfigurationPublisher publisher = 
(DistributedConfigurationPublisher) bean;
+                System.out.println(String.format("\nProcessing commands for 
component : %s", publisher.getComponentName()));
+
+                if (cmdLineOptions.isPublish()) {
+                    System.out.println(String.format("Publishing configuration 
for : %s", publisher.getComponentName()));
+                    publisher.publishConfiguration();
+                    System.out.println(String.format("Published configuration 
for : %s", publisher.getComponentName()));
+                    System.out.printf("\n");
+                }
+
+                if (cmdLineOptions.isVerify()) {
+                    System.out.println(String.format("Verifying configuration 
for : %s", publisher.getComponentName()));
+                    publisher.verifyPublishedConfiguration();
+                    System.out.println(String.format("Verified configuration 
for : %s", publisher.getComponentName()));
+                    System.out.printf("\n");
+                }
+
+                if (cmdLineOptions.isClear()) {
+                    System.out.println(String.format("Clearing configuration 
for : %s", publisher.getComponentName()));
+                    // TODO: 7/2/17 Implement configuration removal
+                    System.out.println(String.format("Cleared configuration 
for : %s", publisher.getComponentName()));
+                    System.out.printf("\n");
+                }
+            }
+        } catch (BeansException e) {
+            logger.error("Error occurred when obtaining configuration 
publisher beans", e);
+            throw e;
+        } catch (Exception e) {
+            logger.error("Error occurred when publishing configuration to 
zookeeper", e);
+            throw e;
+        }
+
+        logger.info("Published configuration successfully");
+    }
+
+    public String getComponentName() {
+        return componentName;
+    }
+}

http://git-wip-us.apache.org/repos/asf/oodt/blob/27a28daa/config/src/main/java/org/apache/oodt/config/distributed/utils/CuratorUtils.java
----------------------------------------------------------------------
diff --git 
a/config/src/main/java/org/apache/oodt/config/distributed/utils/CuratorUtils.java
 
b/config/src/main/java/org/apache/oodt/config/distributed/utils/CuratorUtils.java
index 6f9c97f..1b10ef0 100644
--- 
a/config/src/main/java/org/apache/oodt/config/distributed/utils/CuratorUtils.java
+++ 
b/config/src/main/java/org/apache/oodt/config/distributed/utils/CuratorUtils.java
@@ -100,6 +100,7 @@ public class CuratorUtils {
         int maxRetryCount = 
Integer.parseInt(System.getProperty(Constants.Properties.ZK_CONNECTION_TIMEOUT, 
"3"));
 
         CuratorFrameworkFactory.Builder builder = 
CuratorFrameworkFactory.builder()
+                .namespace(NAMESPACE)
                 .connectString(connectString)
                 .retryPolicy(new ExponentialBackoffRetry(retryInitialWaitMs, 
maxRetryCount))
                 .connectionTimeoutMs(connectionTimeoutMs)

http://git-wip-us.apache.org/repos/asf/oodt/blob/27a28daa/config/src/main/resources/etc/config-publisher.xml
----------------------------------------------------------------------
diff --git a/config/src/main/resources/etc/config-publisher.xml 
b/config/src/main/resources/etc/config-publisher.xml
new file mode 100644
index 0000000..cc1261e
--- /dev/null
+++ b/config/src/main/resources/etc/config-publisher.xml
@@ -0,0 +1,36 @@
+<!--
+  ~ 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.
+  -->
+
+<beans xmlns="http://www.springframework.org/schema/beans";
+       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance";
+       xsi:schemaLocation="http://www.springframework.org/schema/beans 
http://www.springframework.org/schema/beans/spring-beans-2.5.xsd";>
+
+    <bean id="filemgr-config-publisher" 
class="org.apache.oodt.config.distributed.cli.DistributedConfigurationPublisher">
+        <constructor-arg value="filemgr"/>
+        <property name="propertiesFiles">
+            <map key-type="java.lang.String" value-type="java.lang.String">
+                <entry key="../examples/filemgr.properties" 
value="/etc/filemgr.properties"/>
+            </map>
+        </property>
+        <property name="configFiles">
+            <map key-type="java.lang.String" value-type="java.lang.String">
+                <entry key="../examples/mime-types.xml" 
value="/etc/mime-types.xml"/>
+            </map>
+        </property>
+    </bean>
+
+</beans>
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/oodt/blob/27a28daa/config/src/main/resources/etc/log4j.xml
----------------------------------------------------------------------
diff --git a/config/src/main/resources/etc/log4j.xml 
b/config/src/main/resources/etc/log4j.xml
new file mode 100644
index 0000000..8f49451
--- /dev/null
+++ b/config/src/main/resources/etc/log4j.xml
@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="UTF-8" ?>
+<!--
+  ~ 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.
+  -->
+
+<!DOCTYPE log4j:configuration SYSTEM "log4j.dtd">
+
+<log4j:configuration xmlns:log4j="http://jakarta.apache.org/log4j/";>
+    <appender name="console" class="org.apache.log4j.ConsoleAppender">
+        <param name="Target" value="System.out"/>
+        <layout class="org.apache.log4j.PatternLayout">
+            <param name="ConversionPattern" value="%-5p %c{1} - %m%n"/>
+        </layout>
+    </appender>
+
+    <root>
+        <priority value="INFO"/>
+        <appender-ref ref="console"/>
+    </root>
+
+</log4j:configuration>
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/oodt/blob/27a28daa/config/src/main/resources/examples/filemgr.properties
----------------------------------------------------------------------
diff --git a/config/src/main/resources/examples/filemgr.properties 
b/config/src/main/resources/examples/filemgr.properties
new file mode 100644
index 0000000..4d8d957
--- /dev/null
+++ b/config/src/main/resources/examples/filemgr.properties
@@ -0,0 +1,114 @@
+#
+# 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.
+#
+
+# Configuration properties for the File Manager
+
+# repository factory
+filemgr.repository.factory=org.apache.oodt.cas.filemgr.repository.XMLRepositoryManagerFactory
+
+# Lucene catalog factory
+filemgr.catalog.factory=org.apache.oodt.cas.filemgr.catalog.LuceneCatalogFactory
+
+# data transfer factory
+filemgr.datatransfer.factory=org.apache.oodt.cas.filemgr.datatransfer.LocalDataTransferFactory
+
+# validation layer factory
+filemgr.validationLayer.factory=org.apache.oodt.cas.filemgr.validation.XMLValidationLayerFactory
+
+# xml rpc client configuration
+org.apache.oodt.cas.filemgr.system.xmlrpc.connectionTimeout.minutes=20
+org.apache.oodt.cas.filemgr.system.xmlrpc.requestTimeout.minutes=60
+#org.apache.oodt.cas.filemgr.system.xmlrpc.connection.retries=0
+#org.apache.oodt.cas.filemgr.system.xmlrpc.connection.retry.interval.seconds=3
+
+# mapped data source catalog configuration
+#org.apache.oodt.cas.filemgr.catalog.mappeddatasource.mapFile=/path/to/ops.catalog.typemap.properties
+
+# lucene catalog configuration
+org.apache.oodt.cas.filemgr.catalog.lucene.idxPath=[OODT_HOME]/data/catalog
+org.apache.oodt.cas.filemgr.catalog.lucene.pageSize=20
+org.apache.oodt.cas.filemgr.catalog.lucene.commitLockTimeout.seconds=60
+org.apache.oodt.cas.filemgr.catalog.lucene.writeLockTimeout.seconds=60
+org.apache.oodt.cas.filemgr.catalog.lucene.mergeFactor=20
+
+# XML repository manager configuration
+org.apache.oodt.cas.filemgr.repositorymgr.dirs=file:[FILEMGR_HOME]/policy/oodt
+
+# XML validation layer configuration
+org.apache.oodt.cas.filemgr.validation.dirs=file:[FILEMGR_HOME]/policy/oodt
+
+# remote data transfer configuration
+org.apache.oodt.cas.filemgr.datatransfer.remote.chunkSize=1024
+
+# location of Mime-Type repository
+org.apache.oodt.cas.filemgr.mime.type.repository=[FILEMGR_HOME]/etc/mime-types.xml
+
+
+############ data source configuration ##################################
+#
+# These 3 blocks of config properties can be used to setup a catalog,
+# repository manager, and validation layer based on a RDBMS such as
+# Oracle, MySQL, PostgreSQL, or any others that support a jdbc connection.
+# Just un-comment the following blocks of properties and configure as
+# needed.
+#
+#########################################################################
+
+# datasource catalog config
+#org.apache.oodt.cas.filemgr.catalog.datasource.jdbc.url=some_jdbc_url
+#org.apache.oodt.cas.filemgr.catalog.datasource.jdbc.user=user
+#org.apache.oodt.cas.filemgr.catalog.datasource.jdbc.pass=pass
+#org.apache.oodt.cas.filemgr.catalog.datasource.jdbc.driver=driver.class.name
+#org.apache.oodt.cas.filemgr.catalog.datasource.quoteFields=false
+#org.apache.oodt.cas.filemgr.catalog.datasource.pageSize=20
+#org.apache.oodt.cas.filemgr.catalog.datasource.cacheUpdateMinutes=5
+
+# data source repository manager configuration
+#org.apache.oodt.cas.filemgr.repositorymgr.datasource.jdbc.url=some_jdbc_url
+#org.apache.oodt.cas.filemgr.repositorymgr.datasource.jdbc.user=user
+#org.apache.oodt.cas.filemgr.repositorymgr.datasource.jdbc.pass=pass
+#org.apache.oodt.cas.filemgr.repositorymgr.datasource.jdbc.driver=driver.class.name
+
+# data source validation layer configuration
+#org.apache.oodt.cas.filemgr.validation.datasource.jdbc.url=some_jdbc_url
+#org.apache.oodt.cas.filemgr.validation.datasource.jdbc.user=user
+#org.apache.oodt.cas.filemgr.validation.datasource.jdbc.pass=pass
+#org.apache.oodt.cas.filemgr.validation.datasource.jdbc.driver=driver.class.name
+#org.apache.oodt.cas.filemgr.validation.datasource.quoteFields=false
+
+
+# tells the file manager system layer to include product instance metadata
+# NOTE: here are the expected field mappings
+#
+# product.getProductId() -> ProductId
+# product.getProductName() -> ProductName
+# product.getProductStructure() -> ProductStructure
+# product.getTransferStatus() -> ProductTransferStatus
+# product.getRootRef() -> ProductRootReference
+
+# for the references returned by product.getProductReferences() the following
+# metadata fields will be added (order will be maintained, such that data store
+# ref at index 0 will map to orig ref at index 0, etc.)
+#
+# ProductDataStoreReferences (list of all data store references:
+# note already translated into path, not URI)
+# ProductOrigReferences (list of all orig references:
+# note already translated into path, not URI)
+# ProductMimeType (list of all references' mime-types)
+# ProductFileSize (list of all references' file sizes)
+
+org.apache.oodt.cas.filemgr.metadata.expandProduct=false
\ No newline at end of file

Reply via email to