You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@whirr.apache.org by as...@apache.org on 2011/11/09 10:09:46 UTC

svn commit: r1199670 - in /whirr/trunk: ./ core/src/main/java/org/apache/whirr/actions/ core/src/test/java/org/apache/whirr/actions/integration/ core/src/test/resources/ core/src/test/resources/META-INF/services/

Author: asavu
Date: Wed Nov  9 09:09:45 2011
New Revision: 1199670

URL: http://svn.apache.org/viewvc?rev=1199670&view=rev
Log:
WHIRR-409. Add an integration test that shows that there is no overlap between install & configure scripts on the remote machine (asavu)

Added:
    whirr/trunk/core/src/test/java/org/apache/whirr/actions/integration/
    whirr/trunk/core/src/test/java/org/apache/whirr/actions/integration/PhaseExecutionBarrierTest.java
    whirr/trunk/core/src/test/resources/whirr-core-phase-barrier-test.properties
Modified:
    whirr/trunk/CHANGES.txt
    whirr/trunk/core/src/main/java/org/apache/whirr/actions/ScriptBasedClusterAction.java
    whirr/trunk/core/src/test/resources/META-INF/services/org.apache.whirr.ClusterController
    whirr/trunk/core/src/test/resources/META-INF/services/org.apache.whirr.service.ClusterActionHandler

Modified: whirr/trunk/CHANGES.txt
URL: http://svn.apache.org/viewvc/whirr/trunk/CHANGES.txt?rev=1199670&r1=1199669&r2=1199670&view=diff
==============================================================================
--- whirr/trunk/CHANGES.txt (original)
+++ whirr/trunk/CHANGES.txt Wed Nov  9 09:09:45 2011
@@ -72,6 +72,9 @@ Trunk (unreleased changes)
     WHIRR-426. Create a convention for naming clusters used for integration 
     tests (asavu)
 
+    WHIRR-409. Add an integration test that shows that there is no overlap 
+    between install & configure scripts on the remote machine (asavu)
+
   BUG FIXES
 
     WHIRR-377. Fix broken CLI logging config. (asavu via tomwhite)

Modified: whirr/trunk/core/src/main/java/org/apache/whirr/actions/ScriptBasedClusterAction.java
URL: http://svn.apache.org/viewvc/whirr/trunk/core/src/main/java/org/apache/whirr/actions/ScriptBasedClusterAction.java?rev=1199670&r1=1199669&r2=1199670&view=diff
==============================================================================
--- whirr/trunk/core/src/main/java/org/apache/whirr/actions/ScriptBasedClusterAction.java (original)
+++ whirr/trunk/core/src/main/java/org/apache/whirr/actions/ScriptBasedClusterAction.java Wed Nov  9 09:09:45 2011
@@ -207,8 +207,9 @@ public abstract class ScriptBasedCluster
       try {
         ExecResponse execResponse = future.get();
         if (execResponse.getExitCode() != 0) {
-          LOG.error("Error running script: {}\n{}", execResponse.getError(),
-              execResponse.getOutput());
+          LOG.error("Error running " + phaseName + " script: {}", execResponse);
+        } else {
+          LOG.info("Successfully executed {} script: {}", phaseName, execResponse);
         }
       } catch (ExecutionException e) {
         throw new IOException(e.getCause());
@@ -222,11 +223,11 @@ public abstract class ScriptBasedCluster
 
   protected void eventSpecificActions(
       Entry<InstanceTemplate, ClusterActionEvent> entry) throws IOException {
-  };
+  }
 
   protected void postRunScriptsActions(
       Map<InstanceTemplate, ClusterActionEvent> eventMap) throws IOException {
-  };
+  }
 
   /**
    * Try to get an {@see ClusterActionHandler } instance or throw an

Added: whirr/trunk/core/src/test/java/org/apache/whirr/actions/integration/PhaseExecutionBarrierTest.java
URL: http://svn.apache.org/viewvc/whirr/trunk/core/src/test/java/org/apache/whirr/actions/integration/PhaseExecutionBarrierTest.java?rev=1199670&view=auto
==============================================================================
--- whirr/trunk/core/src/test/java/org/apache/whirr/actions/integration/PhaseExecutionBarrierTest.java (added)
+++ whirr/trunk/core/src/test/java/org/apache/whirr/actions/integration/PhaseExecutionBarrierTest.java Wed Nov  9 09:09:45 2011
@@ -0,0 +1,185 @@
+/**
+ * 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.whirr.actions.integration;
+
+import com.google.common.base.Predicates;
+import com.google.common.collect.Iterables;
+import com.google.common.collect.Maps;
+import org.apache.commons.configuration.Configuration;
+import org.apache.commons.configuration.ConfigurationException;
+import org.apache.commons.configuration.PropertiesConfiguration;
+import org.apache.commons.ssl.asn1.Strings;
+import org.apache.whirr.ClusterController;
+import org.apache.whirr.ClusterControllerFactory;
+import org.apache.whirr.ClusterSpec;
+import org.apache.whirr.service.ClusterActionEvent;
+import org.apache.whirr.service.ClusterActionHandlerSupport;
+import org.jclouds.compute.domain.ExecResponse;
+import org.jclouds.compute.domain.NodeMetadata;
+import org.jclouds.scriptbuilder.domain.Statements;
+import org.junit.Test;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.util.Map;
+import java.util.concurrent.ConcurrentMap;
+
+import static java.lang.Integer.parseInt;
+import static org.apache.commons.lang.StringUtils.deleteWhitespace;
+import static org.jclouds.scriptbuilder.domain.Statements.exec;
+import static org.junit.Assert.assertTrue;
+
+public class PhaseExecutionBarrierTest {
+
+  private static final Logger LOG = LoggerFactory
+      .getLogger(PhaseExecutionBarrierTest.class);
+
+  private static final ConcurrentMap<String, Long> STEP_TIMES = Maps.newConcurrentMap();
+
+  private static long getUnixTime() {
+    return System.currentTimeMillis() / 1000L;
+  }
+
+  private static void recordTime(String name) {
+    STEP_TIMES.put(name, getUnixTime());
+  }
+
+  /**
+   * A special role implementation that can be used for testing that
+   * the install and the configure phase do not overlap
+   */
+  static public class PhaseBarrierTestActionHandler
+    extends ClusterActionHandlerSupport {
+
+    @Override
+    public String getRole() {
+      return "phase-barrier-test";
+    }
+
+    /**
+     * Record timestamps for this phase execution on the remote machine
+     */
+    @Override
+    public void beforeBootstrap(ClusterActionEvent event) {
+      addStatement(event, Statements.newStatementList(
+        exec("date +%s > /tmp/bootstrap-start"),
+        exec("sleep 60"), // 1 minute
+        exec("date +%s > /tmp/bootstrap-end")
+      ));
+
+      recordTime("before-bootstrap");
+    }
+
+    @Override
+    public void afterBootstrap(ClusterActionEvent event) {
+      recordTime("after-bootstrap");
+      /* Note: Scripts are not executed for this step */
+    }
+
+    /**
+     * Record the timestamp for this phase execution
+     */
+    @Override
+    public void beforeConfigure(ClusterActionEvent event) {
+      recordTime("before-configure");
+      addStatement(event, exec("date +%s > /tmp/configure-start"));
+    }
+
+    @Override
+    public void afterConfigure(ClusterActionEvent event) {
+      recordTime("after-configure");
+      /* Note: Scripts are not executed for this step */
+    }
+
+    @Override
+    public void beforeDestroy(ClusterActionEvent event) {
+      recordTime("before-destroy");
+      addStatement(event, exec("data +%s > /tmp/destroy-start"));
+    }
+
+    @Override
+    public void afterDestroy(ClusterActionEvent event) {
+      recordTime("after-destroy");
+      /* Note: Scripts are not executed for this step */
+    }
+  }
+
+  private Configuration getTestConfiguration() throws ConfigurationException {
+    return new PropertiesConfiguration("whirr-core-phase-barrier-test.properties");
+  }
+
+  private ClusterSpec getTestClusterSpec() throws Exception {
+    return ClusterSpec.withTemporaryKeys(getTestConfiguration());
+  }
+
+  @Test
+  public void testNoRemoteExecutionOverlap() throws Exception {
+    ClusterSpec spec = getTestClusterSpec();
+    ClusterController controller =
+      (new ClusterControllerFactory()).create(spec.getServiceName());
+
+    try {
+      controller.launchCluster(spec);
+      Map<? extends NodeMetadata, ExecResponse> responseMap = controller.runScriptOnNodesMatching(
+        spec,
+        Predicates.<NodeMetadata>alwaysTrue(),
+        exec("cat /tmp/bootstrap-start /tmp/bootstrap-end /tmp/configure-start")
+      );
+      ExecResponse response = Iterables.get(responseMap.values(), 0);
+      LOG.info("Got response: {}", response);
+
+      String[] parts = Strings.split(response.getOutput(), '\n');
+
+      int bootstrapStart = parseInt(deleteWhitespace(parts[0]));
+      int bootstrapEnd = parseInt(deleteWhitespace(parts[1]));
+      int configureStart = parseInt(deleteWhitespace(parts[2]));
+
+      assertTrue(bootstrapStart < bootstrapEnd);
+      assertTrue(bootstrapEnd < configureStart);
+
+    } finally {
+      controller.destroyCluster(spec);
+    }
+
+    assertNoOverlapOnLocalMachine();
+  }
+
+  private void assertNoOverlapOnLocalMachine() {
+    String[] listOfSteps = new String[] {"bootstrap", "configure", "destroy"};
+
+    for(int i = 0; i < listOfSteps.length; i += 1) {
+      String currentStep = listOfSteps[i];
+
+      assertTrue(
+        String.format("Overlap while running '%s'", currentStep),
+        STEP_TIMES.get("before-" + currentStep) <= STEP_TIMES.get("after-" + currentStep)
+      );
+
+      if (i < (listOfSteps.length - 1)) {
+        String nextStep = listOfSteps[i + 1];
+
+        assertTrue(
+          String.format("Overlap '%s' and '%s'", currentStep, nextStep),
+          STEP_TIMES.get("after-" + currentStep) <= STEP_TIMES.get("before-" + nextStep)
+        );
+      }
+    }
+  }
+
+}

Modified: whirr/trunk/core/src/test/resources/META-INF/services/org.apache.whirr.ClusterController
URL: http://svn.apache.org/viewvc/whirr/trunk/core/src/test/resources/META-INF/services/org.apache.whirr.ClusterController?rev=1199670&r1=1199669&r2=1199670&view=diff
==============================================================================
--- whirr/trunk/core/src/test/resources/META-INF/services/org.apache.whirr.ClusterController (original)
+++ whirr/trunk/core/src/test/resources/META-INF/services/org.apache.whirr.ClusterController Wed Nov  9 09:09:45 2011
@@ -9,4 +9,4 @@
 #   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.
-org.apache.whirr.ClusterControllerFactoryTest$TestClusterController
\ No newline at end of file
+org.apache.whirr.ClusterControllerFactoryTest$TestClusterController

Modified: whirr/trunk/core/src/test/resources/META-INF/services/org.apache.whirr.service.ClusterActionHandler
URL: http://svn.apache.org/viewvc/whirr/trunk/core/src/test/resources/META-INF/services/org.apache.whirr.service.ClusterActionHandler?rev=1199670&r1=1199669&r2=1199670&view=diff
==============================================================================
--- whirr/trunk/core/src/test/resources/META-INF/services/org.apache.whirr.service.ClusterActionHandler (original)
+++ whirr/trunk/core/src/test/resources/META-INF/services/org.apache.whirr.service.ClusterActionHandler Wed Nov  9 09:09:45 2011
@@ -11,4 +11,5 @@
 #   limitations under the License.
 org.apache.whirr.service.NoopClusterActionHandler
 org.apache.whirr.service.DryRunModuleTest$Noop2ClusterActionHandler
-org.apache.whirr.service.DryRunModuleTest$Noop3ClusterActionHandler
\ No newline at end of file
+org.apache.whirr.service.DryRunModuleTest$Noop3ClusterActionHandler
+org.apache.whirr.actions.integration.PhaseExecutionBarrierTest$PhaseBarrierTestActionHandler
\ No newline at end of file

Added: whirr/trunk/core/src/test/resources/whirr-core-phase-barrier-test.properties
URL: http://svn.apache.org/viewvc/whirr/trunk/core/src/test/resources/whirr-core-phase-barrier-test.properties?rev=1199670&view=auto
==============================================================================
--- whirr/trunk/core/src/test/resources/whirr-core-phase-barrier-test.properties (added)
+++ whirr/trunk/core/src/test/resources/whirr-core-phase-barrier-test.properties Wed Nov  9 09:09:45 2011
@@ -0,0 +1,27 @@
+#
+# 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.
+#
+whirr.cluster-name=core-phase-barrier-test-${sys:whirr.test.provider}-${sys:user.name}
+whirr.instance-templates=1 phase-barrier-test
+
+whirr.provider=${sys:whirr.test.provider}
+whirr.identity=${sys:whirr.test.identity}
+whirr.credential=${sys:whirr.test.credential}
+
+# Waiting until http://code.google.com/p/jclouds/issues/detail?id=746 
+# whirr.hardware-min-ram=512
+