brooklyn-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From henev...@apache.org
Subject [27/50] brooklyn-server git commit: return quickly on attempts to look up external ip address, so we don't block excessively when network is dodgy; and misc tidies elsewhere for better http test routings and logging on duplicated sensor definitions
Date Mon, 01 Feb 2016 17:48:57 GMT
return quickly on attempts to look up external ip address, so we don't block excessively when
network is dodgy;
and misc tidies elsewhere for better http test routings and logging on duplicated sensor definitions


Project: http://git-wip-us.apache.org/repos/asf/brooklyn-server/repo
Commit: http://git-wip-us.apache.org/repos/asf/brooklyn-server/commit/2da0cf6b
Tree: http://git-wip-us.apache.org/repos/asf/brooklyn-server/tree/2da0cf6b
Diff: http://git-wip-us.apache.org/repos/asf/brooklyn-server/diff/2da0cf6b

Branch: refs/heads/0.4.0
Commit: 2da0cf6bf0a2e99b54b7564365e159b90abef664
Parents: a0e7c13
Author: Alex Heneveld <alex.heneveld@cloudsoftcorp.com>
Authored: Wed Oct 10 00:50:46 2012 +0100
Committer: Alex Heneveld <alex.heneveld@cloudsoftcorp.com>
Committed: Wed Oct 10 00:50:46 2012 +0100

----------------------------------------------------------------------
 .../entity/basic/EntityDynamicType.java         | 16 ++++--
 .../location/geo/UtraceHostGeoLookup.java       | 51 ++++++++++++++++++--
 core/src/main/java/brooklyn/util/Time.java      |  2 +
 .../brooklyn/util/internal/TimeExtras.groovy    | 19 ++++++--
 .../main/java/brooklyn/test/HttpTestUtils.java  | 34 +++++++++++++
 .../main/java/brooklyn/test/TestUtils.groovy    | 15 ++++--
 6 files changed, 121 insertions(+), 16 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/brooklyn-server/blob/2da0cf6b/core/src/main/java/brooklyn/entity/basic/EntityDynamicType.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/brooklyn/entity/basic/EntityDynamicType.java b/core/src/main/java/brooklyn/entity/basic/EntityDynamicType.java
index c1f5701..0024e3b 100644
--- a/core/src/main/java/brooklyn/entity/basic/EntityDynamicType.java
+++ b/core/src/main/java/brooklyn/entity/basic/EntityDynamicType.java
@@ -176,12 +176,14 @@ public class EntityDynamicType {
         try {
             Class<? extends Entity> clazz = entity.getClass();
             Map<String,Effector<?>> result = Maps.newLinkedHashMap();
+            Map<String,Field> sources = Maps.newLinkedHashMap();
             for (Field f : clazz.getFields()) {
                 if (Effector.class.isAssignableFrom(f.getType())) {
                     Effector<?> eff = (Effector<?>) f.get(entity);
                     Effector<?> overwritten = result.put(eff.getName(), eff);
+                    Field source = sources.put(eff.getName(), f);
                     if (overwritten!=null && overwritten != eff) 
-                        LOG.warn("multiple definitions for effector {} on {}; preferring
{} to {}", new Object[] {eff.getName(), entity, eff, overwritten});
+                        LOG.warn("multiple definitions for effector {} on {}; preferring
{} from {} to {} from {}", new Object[] {eff.getName(), entity, eff, f, overwritten, source});
                 }
             }
             
@@ -198,12 +200,20 @@ public class EntityDynamicType {
         try {
             Class<? extends Entity> clazz = entity.getClass();
             Map<String,Sensor<?>> result = Maps.newLinkedHashMap();
+            Map<String,Field> sources = Maps.newLinkedHashMap();
             for (Field f : clazz.getFields()) {
                 if (Sensor.class.isAssignableFrom(f.getType())) {
                     Sensor<?> sens = (Sensor<?>) f.get(entity);
                     Sensor<?> overwritten = result.put(sens.getName(), sens);
-                    if (overwritten!=null && overwritten != sens) 
-                        LOG.warn("multiple definitions for sensor {} on {}; preferring {}
to {}", new Object[] {sens.getName(), entity, sens, overwritten});
+                    Field source = sources.put(sens.getName(), f);
+                    if (overwritten!=null && overwritten != sens) {
+                        if (sens instanceof HasConfigKey) {
+                            // probably overriding defaults, just log as debug (there will
be add'l logging in config key section)
+                            LOG.debug("multiple definitions for config sensor {} on {}; preferring
{} from {} to {} from {}", new Object[] {sens.getName(), entity, sens, f, overwritten, source});
+                        } else {
+                            LOG.warn("multiple definitions for sensor {} on {}; preferring
{} from {} to {} from {}", new Object[] {sens.getName(), entity, sens, f, overwritten, source});
+                        }
+                    }
                 }
             }
 

http://git-wip-us.apache.org/repos/asf/brooklyn-server/blob/2da0cf6b/core/src/main/java/brooklyn/location/geo/UtraceHostGeoLookup.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/brooklyn/location/geo/UtraceHostGeoLookup.java b/core/src/main/java/brooklyn/location/geo/UtraceHostGeoLookup.java
index 9a41344..221534c 100644
--- a/core/src/main/java/brooklyn/location/geo/UtraceHostGeoLookup.java
+++ b/core/src/main/java/brooklyn/location/geo/UtraceHostGeoLookup.java
@@ -7,15 +7,18 @@ import groovy.util.XmlParser;
 import java.io.IOException;
 import java.net.InetAddress;
 import java.net.MalformedURLException;
+import java.net.URL;
+import java.net.URLConnection;
+import java.util.concurrent.atomic.AtomicBoolean;
 
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
-import com.google.common.base.Throwables;
-
 import brooklyn.util.NetworkUtils;
 import brooklyn.util.ResourceUtils;
 
+import com.google.common.base.Throwables;
+
 public class UtraceHostGeoLookup implements HostGeoLookup {
 
     /*
@@ -51,11 +54,49 @@ Beyond this you get blacklisted and requests may time out, or return none.
         return "http://xml.utrace.de/?query="+ip.trim();
     }
 
-    static String localExternalIp;
+    static AtomicBoolean retrievingLocalExternalIp = new AtomicBoolean(false); 
+    volatile static String localExternalIp;
     /** returns public IP of localhost */
-    public synchronized static String getLocalhostExternalIp() {
+    public static synchronized String getLocalhostExternalIp() {
         if (localExternalIp!=null) return localExternalIp;
-        localExternalIp = new ResourceUtils(HostGeoLookup.class).getResourceAsString("http://api.externalip.net/ip/").trim();
+
+        // do in private thread, otherwise blocks for 30s+ on dodgy network!
+        // (we can skip it if someone else is doing it, we have synch lock so we'll get notified)
+        if (!retrievingLocalExternalIp.get())
+            new Thread(new Runnable() {
+                public void run() {
+                    if (retrievingLocalExternalIp.getAndSet(true))
+                        // someone else already trying to retrieve; caller can safely just
wait,
+                        // as they will get notified by the someone else
+                        return;
+                    try {
+                        if (localExternalIp!=null)
+                            // someone else succeeded
+                            return;
+                        log.debug("Looking up external IP of this host in private thread
"+Thread.currentThread());
+                        localExternalIp = new ResourceUtils(HostGeoLookup.class).getResourceAsString("http://api.externalip.net/ip/").trim();
+                        log.debug("Finished looking up external IP of this host in private
thread, result "+localExternalIp);
+                    } catch (Throwable t) {
+                        log.debug("Not able to look up external IP of this host in private
thread, probably offline ("+t+")");
+                    } finally {
+                        synchronized (UtraceHostGeoLookup.class) {
+                            UtraceHostGeoLookup.class.notifyAll();        
+                            retrievingLocalExternalIp.set(false);
+                        }
+                    }
+                }
+            }).start();
+        
+        try {
+            // only wait 2s, so startup is fast
+            UtraceHostGeoLookup.class.wait(2000);
+        } catch (InterruptedException e) {
+            throw Throwables.propagate(e);
+        }
+        if (localExternalIp==null) throw 
+            Throwables.propagate(new IOException("Unable to discover external IP of local
machine; response to server timed out (thread may be ongoing)"));
+        
+        log.debug("Looked up external IP of this host, result is: "+localExternalIp);
         return localExternalIp;
     }
     public String getLookupUrlForLocalhost() {

http://git-wip-us.apache.org/repos/asf/brooklyn-server/blob/2da0cf6b/core/src/main/java/brooklyn/util/Time.java
----------------------------------------------------------------------
diff --git a/core/src/main/java/brooklyn/util/Time.java b/core/src/main/java/brooklyn/util/Time.java
index d59240a..0aa32b3 100644
--- a/core/src/main/java/brooklyn/util/Time.java
+++ b/core/src/main/java/brooklyn/util/Time.java
@@ -147,6 +147,7 @@ public class Time {
 		return result;
 	}
 
+	/** sleep which propagates Interrupted as unchecked */
 	public static void sleep(long millis) {
 		try {
 			Thread.sleep(millis);
@@ -275,4 +276,5 @@ public class Time {
 			return d*multiplier + dd;
 		}
 	}
+	
 }

http://git-wip-us.apache.org/repos/asf/brooklyn-server/blob/2da0cf6b/core/src/main/java/brooklyn/util/internal/TimeExtras.groovy
----------------------------------------------------------------------
diff --git a/core/src/main/java/brooklyn/util/internal/TimeExtras.groovy b/core/src/main/java/brooklyn/util/internal/TimeExtras.groovy
index 7a694a9..61c5169 100644
--- a/core/src/main/java/brooklyn/util/internal/TimeExtras.groovy
+++ b/core/src/main/java/brooklyn/util/internal/TimeExtras.groovy
@@ -3,12 +3,12 @@ package brooklyn.util.internal
 import groovy.time.TimeDuration
 
 import java.util.concurrent.TimeUnit
-import java.util.concurrent.atomic.AtomicBoolean
 
-import org.codehaus.groovy.reflection.ClassInfo;
 import org.slf4j.Logger
 import org.slf4j.LoggerFactory
 
+import brooklyn.util.Time
+
 
 /**
  * Classloading this class will cause multiply/add to be made available on TimeDuration.
@@ -44,6 +44,19 @@ class TimeExtras {
      * where an int may get constructed too early and not have the multiply syntax available
      * (because grail is invoked?; if e.g. 5*SECONDS throws an error, try duration(5, SECONDS)
 */ 
     public static TimeDuration duration(int value, TimeUnit unit) {
-        return new TimeDuration(unit.toMillis(value));
+        return new TimeDuration(0, 0, 0, (int)unit.toMillis(value));
     }
+    
+    public static final TimeDuration ONE_SECOND = duration(1, TimeUnit.SECONDS);
+    public static final TimeDuration FIVE_SECONDS = duration(5, TimeUnit.SECONDS);
+    public static final TimeDuration TEN_SECONDS = duration(10, TimeUnit.SECONDS);
+    public static final TimeDuration THIRTY_SECONDS = duration(30, TimeUnit.SECONDS);
+    public static final TimeDuration ONE_MINUTE = duration(1, TimeUnit.MINUTES);
+    public static final TimeDuration TWO_MINUTES = duration(2, TimeUnit.MINUTES);
+    public static final TimeDuration FIVE_MINUTES = duration(5, TimeUnit.MINUTES);
+
+    public static void sleep(TimeDuration duration) {
+        Time.sleep(duration.toMilliseconds());
+    }    
+    
 }

http://git-wip-us.apache.org/repos/asf/brooklyn-server/blob/2da0cf6b/usage/test-support/src/main/java/brooklyn/test/HttpTestUtils.java
----------------------------------------------------------------------
diff --git a/usage/test-support/src/main/java/brooklyn/test/HttpTestUtils.java b/usage/test-support/src/main/java/brooklyn/test/HttpTestUtils.java
index a64adfa..a9167fe 100644
--- a/usage/test-support/src/main/java/brooklyn/test/HttpTestUtils.java
+++ b/usage/test-support/src/main/java/brooklyn/test/HttpTestUtils.java
@@ -10,6 +10,7 @@ import java.io.IOException;
 import java.net.HttpURLConnection;
 import java.net.URL;
 import java.net.URLConnection;
+import java.util.Collections;
 import java.util.Map;
 import java.util.NoSuchElementException;
 
@@ -17,10 +18,13 @@ import javax.net.ssl.HostnameVerifier;
 import javax.net.ssl.HttpsURLConnection;
 import javax.net.ssl.SSLSession;
 
+import org.codehaus.groovy.runtime.DefaultGroovyMethods;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
+import org.testng.Assert;
 
 import com.google.common.base.Throwables;
+import com.google.common.collect.Lists;
 import com.google.common.collect.Maps;
 import com.google.common.util.concurrent.ListenableFuture;
 import com.google.common.util.concurrent.ListeningExecutorService;
@@ -108,6 +112,36 @@ public class HttpTestUtils {
          });
     }
 
+    public static void assertContentContainsText(final String url, final String phrase, final
String ...additionalPhrases) {
+        try {
+            String contents = DefaultGroovyMethods.getText(new URL(url).openStream());
+            Assert.assertTrue(contents!=null && contents.length()>0);
+            for (String text: Lists.asList(phrase, additionalPhrases)) {
+                if (!contents.contains(text)) {
+                    LOG.warn("CONTENTS OF URL "+url+" MISSING TEXT: "+text+"\n"+contents);
+                    Assert.fail("URL "+url+" does not contain text: "+text);
+                }
+            }
+        } catch (Exception e) {
+            throw Throwables.propagate(e);
+        }
+    }
+
+    public static void assertContentEventuallyContainsText(Map flags, final String url, final
String phrase, final String ...additionalPhrases) {
+        TestUtils.executeUntilSucceeds(new Runnable() {
+            public void run() {
+                assertContentContainsText(url, phrase, additionalPhrases);
+            }
+         });
+    }
+    public static void assertContentEventuallyContainsText(final String url, final String
phrase, final String ...additionalPhrases) {
+        assertContentEventuallyContainsText(Collections.emptyMap(), url, phrase, additionalPhrases);
+    }
+
+    /** @deprecated since 0.4.0 use assertContentEventuallyContainsText */
+    // it's not necessarily http (and http is implied by the class name anyway)
+    // more importantly, we want to use new routines above which don't wrap execute-until-succeeds
twice!
+    @Deprecated
     public static void assertHttpContentEventuallyContainsText(final String url, final String
containedText) {
         TestUtils.executeUntilSucceeds(new Runnable() {
             public void run() {

http://git-wip-us.apache.org/repos/asf/brooklyn-server/blob/2da0cf6b/usage/test-support/src/main/java/brooklyn/test/TestUtils.groovy
----------------------------------------------------------------------
diff --git a/usage/test-support/src/main/java/brooklyn/test/TestUtils.groovy b/usage/test-support/src/main/java/brooklyn/test/TestUtils.groovy
index d2d340f..1c7a828 100644
--- a/usage/test-support/src/main/java/brooklyn/test/TestUtils.groovy
+++ b/usage/test-support/src/main/java/brooklyn/test/TestUtils.groovy
@@ -188,14 +188,14 @@ public class TestUtils {
         TimeDuration fixedPeriod = toTimeDuration(flags.period) ?: null
         TimeDuration minPeriod = fixedPeriod ?: toTimeDuration(flags.minPeriod) ?: new TimeDuration(0,0,0,1)
         TimeDuration maxPeriod = fixedPeriod ?: toTimeDuration(flags.maxPeriod) ?: new TimeDuration(0,0,0,500)
-        int maxAttempts = flags.maxAttempts ?: Integer.MAX_VALUE
+        int maxAttempts = flags.maxAttempts ?: Integer.MAX_VALUE;
+        int attempt = 0;
+        long startTime = System.currentTimeMillis();
         try {
             Throwable lastException = null;
             Object result;
             long lastAttemptTime = 0;
-            long startTime = System.currentTimeMillis()
-            long expireTime = startTime+duration.toMilliseconds()
-            int attempt = 0;
+            long expireTime = startTime+duration.toMilliseconds();
             long sleepTimeBetweenAttempts = minPeriod.toMilliseconds();
             
             while (attempt<maxAttempts && lastAttemptTime<expireTime) {
@@ -229,7 +229,9 @@ public class TestUtils {
                 throw lastException
             fail "invalid result: $result"
         } catch (Throwable t) {
-			if (logException) log.info("failed execute-until-succeeds (rethrowing): "+t)
+			if (logException) log.info("failed execute-until-succeeds, "+attempt+" attempts, "+
+                (System.currentTimeMillis()-startTime)+"ms elapsed "+
+                "(rethrowing): "+t);
 			throw t
         } finally {
             finallyBlock.call()
@@ -319,6 +321,9 @@ public class TestUtils {
         }
     }
     
+    /** @deprecated since 0.4.0 use HttpTestUtils.assertUrlEventuallyHasText or HttpTestUtils.assertUrlHasText

+     * (NB: this method has "eventually" logic, with default timeout of 30s, despite the
absence of that in the name) */
+    @Deprecated
     public static void assertUrlHasText(Map flags=[:], String url, String ...phrases) {
         String contents;
         TimeDuration timeout = flags.timeout in Number ? flags.timeout*TimeUnit.MILLISECONDS
: flags.timeout ?: 30*TimeUnit.SECONDS


Mime
View raw message