Return-Path: X-Original-To: archive-asf-public-internal@cust-asf2.ponee.io Delivered-To: archive-asf-public-internal@cust-asf2.ponee.io Received: from cust-asf.ponee.io (cust-asf.ponee.io [163.172.22.183]) by cust-asf2.ponee.io (Postfix) with ESMTP id 7DF36200B81 for ; Tue, 13 Sep 2016 21:12:03 +0200 (CEST) Received: by cust-asf.ponee.io (Postfix) id 7CB18160AD2; Tue, 13 Sep 2016 19:12:03 +0000 (UTC) Delivered-To: archive-asf-public@cust-asf.ponee.io Received: from mail.apache.org (hermes.apache.org [140.211.11.3]) by cust-asf.ponee.io (Postfix) with SMTP id A2243160AD8 for ; Tue, 13 Sep 2016 21:12:01 +0200 (CEST) Received: (qmail 11755 invoked by uid 500); 13 Sep 2016 19:12:00 -0000 Mailing-List: contact commits-help@geode.incubator.apache.org; run by ezmlm Precedence: bulk List-Help: List-Unsubscribe: List-Post: List-Id: Reply-To: dev@geode.incubator.apache.org Delivered-To: mailing list commits@geode.incubator.apache.org Received: (qmail 11670 invoked by uid 99); 13 Sep 2016 19:12:00 -0000 Received: from pnap-us-west-generic-nat.apache.org (HELO spamd3-us-west.apache.org) (209.188.14.142) by apache.org (qpsmtpd/0.29) with ESMTP; Tue, 13 Sep 2016 19:12:00 +0000 Received: from localhost (localhost [127.0.0.1]) by spamd3-us-west.apache.org (ASF Mail Server at spamd3-us-west.apache.org) with ESMTP id 607DA180672 for ; Tue, 13 Sep 2016 19:12:00 +0000 (UTC) X-Virus-Scanned: Debian amavisd-new at spamd3-us-west.apache.org X-Spam-Flag: NO X-Spam-Score: -4.646 X-Spam-Level: X-Spam-Status: No, score=-4.646 tagged_above=-999 required=6.31 tests=[KAM_ASCII_DIVIDERS=0.8, KAM_LAZY_DOMAIN_SECURITY=1, RCVD_IN_DNSWL_HI=-5, RCVD_IN_MSPIKE_H3=-0.01, RCVD_IN_MSPIKE_WL=-0.01, RP_MATCHES_RCVD=-1.426] autolearn=disabled Received: from mx1-lw-eu.apache.org ([10.40.0.8]) by localhost (spamd3-us-west.apache.org [10.40.0.10]) (amavisd-new, port 10024) with ESMTP id Zs2v2EcrnDQi for ; Tue, 13 Sep 2016 19:11:55 +0000 (UTC) Received: from mail.apache.org (hermes.apache.org [140.211.11.3]) by mx1-lw-eu.apache.org (ASF Mail Server at mx1-lw-eu.apache.org) with SMTP id 70B2260E2B for ; Tue, 13 Sep 2016 19:11:49 +0000 (UTC) Received: (qmail 8470 invoked by uid 99); 13 Sep 2016 19:11:48 -0000 Received: from git1-us-west.apache.org (HELO git1-us-west.apache.org) (140.211.11.23) by apache.org (qpsmtpd/0.29) with ESMTP; Tue, 13 Sep 2016 19:11:48 +0000 Received: by git1-us-west.apache.org (ASF Mail Server at git1-us-west.apache.org, from userid 33) id 5F72CE97DD; Tue, 13 Sep 2016 19:11:48 +0000 (UTC) Content-Type: text/plain; charset="us-ascii" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit From: udo@apache.org To: commits@geode.incubator.apache.org Date: Tue, 13 Sep 2016 19:11:58 -0000 Message-Id: <1cceee1e841e4059bff72d940399387d@git.apache.org> In-Reply-To: References: X-Mailer: ASF-Git Admin Mailer Subject: [11/50] [abbrv] incubator-geode git commit: Merge branch 'develop' into feature/GEODE-420 archived-at: Tue, 13 Sep 2016 19:12:03 -0000 http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/dfbc88b2/geode-core/src/test/java/com/gemstone/gemfire/internal/statistics/GemFireStatSamplerIntegrationTest.java ---------------------------------------------------------------------- diff --cc geode-core/src/test/java/com/gemstone/gemfire/internal/statistics/GemFireStatSamplerIntegrationTest.java index 0000000,ff7c34d..0e87a47 mode 000000,100644..100644 --- a/geode-core/src/test/java/com/gemstone/gemfire/internal/statistics/GemFireStatSamplerIntegrationTest.java +++ b/geode-core/src/test/java/com/gemstone/gemfire/internal/statistics/GemFireStatSamplerIntegrationTest.java @@@ -1,0 -1,612 +1,616 @@@ + /* + * 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 com.gemstone.gemfire.internal.statistics; + + import static com.gemstone.gemfire.distributed.ConfigurationProperties.*; + import static org.junit.Assert.*; + import static org.junit.Assume.*; + + import java.io.File; + import java.lang.reflect.Method; + import java.util.Arrays; + import java.util.List; + import java.util.Properties; + import java.util.concurrent.atomic.AtomicBoolean; + import java.util.concurrent.atomic.AtomicInteger; + + import org.apache.logging.log4j.Logger; + import org.junit.After; + import org.junit.Assert; + import org.junit.Before; + import org.junit.Rule; + import org.junit.Test; + import org.junit.experimental.categories.Category; + import org.junit.rules.TemporaryFolder; + import org.junit.rules.TestName; + + import com.gemstone.gemfire.Statistics; + import com.gemstone.gemfire.StatisticsType; + import com.gemstone.gemfire.distributed.DistributedSystem; + import com.gemstone.gemfire.distributed.internal.InternalDistributedSystem; + import com.gemstone.gemfire.internal.GemFireVersion; + import com.gemstone.gemfire.internal.PureJavaMode; + import com.gemstone.gemfire.internal.SocketCreator; + import com.gemstone.gemfire.internal.cache.control.HeapMemoryMonitor; + import com.gemstone.gemfire.internal.logging.LogService; ++import com.gemstone.gemfire.internal.net.SocketCreator; ++import com.gemstone.gemfire.internal.statistics.SampleCollector; ++import com.gemstone.gemfire.internal.statistics.StatArchiveHandler; ++import com.gemstone.gemfire.internal.statistics.StatArchiveHandlerConfig; + import com.gemstone.gemfire.internal.statistics.GemFireStatSampler.LocalStatListenerImpl; + import com.gemstone.gemfire.internal.statistics.platform.OsStatisticsFactory; + import com.gemstone.gemfire.internal.statistics.platform.ProcessStats; + import com.gemstone.gemfire.internal.stats50.VMStats50; + import com.gemstone.gemfire.internal.util.StopWatch; + import com.gemstone.gemfire.test.junit.categories.IntegrationTest; + + /** + * Integration tests for {@link GemFireStatSampler}. + * + * @since GemFire 7.0 + */ + @Category(IntegrationTest.class) + public class GemFireStatSamplerIntegrationTest extends StatSamplerTestCase { + + private static final Logger logger = LogService.getLogger(); + + private static final int STAT_SAMPLE_RATE = 1000; + + private DistributedSystem system; + private File testDir; + + @Rule + public TemporaryFolder temporaryFolder = new TemporaryFolder(); + + @Rule + public TestName testName = new TestName(); - ++ + @Before + public void setUp() throws Exception { + this.testDir = this.temporaryFolder.getRoot(); + assertTrue(this.testDir.exists()); + } + + /** + * Removes the loner DistributedSystem at the end of each test. + */ + @After + public void tearDown() throws Exception { + System.clearProperty(GemFireStatSampler.TEST_FILE_SIZE_LIMIT_IN_KB_PROPERTY); + disconnect(); + } + + /** + * Tests the majority of getters and the basic functionality of the sampler. + * + * This test is skipped when running on Windows 7 because ProcessStats is not created for this OS. See #45395. + */ + @Test + public void testBasics() throws Exception { + final String osName = System.getProperty("os.name", "unknown"); + assumeFalse(osName.equals("Windows 7")); + + connect(createGemFireProperties()); + + GemFireStatSampler statSampler = getGemFireStatSampler(); + assertTrue(statSampler.waitForInitialization(5000)); + + assertEquals(0, statSampler.getArchiveFileSizeLimit()); + assertEquals(0, statSampler.getArchiveDiskSpaceLimit()); + assertEquals(STAT_SAMPLE_RATE, statSampler.getSampleRate()); + assertEquals(true, statSampler.isSamplingEnabled()); + + int statsCount = statSampler.getStatisticsManager().getStatisticsCount(); + + assertEquals(statsCount, statSampler.getStatisticsModCount()); + assertEquals(statsCount, statSampler.getStatisticsManager().getStatisticsCount()); + assertEquals(statsCount, statSampler.getStatistics().length); + + Assert.assertEquals(getStatisticsManager().getId(), statSampler.getSystemId()); + assertTrue(statSampler.getSystemStartTime() < System.currentTimeMillis()); + Assert.assertEquals(SocketCreator.getHostName(SocketCreator.getLocalHost()), + statSampler.getSystemDirectoryPath()); + + AllStatistics allStats = new AllStatistics(statSampler); + + VMStatsContract vmStats = statSampler.getVMStats(); + assertNotNull(vmStats); + assertTrue(vmStats instanceof VMStats50); + /* NOTE: VMStats50 is not an instance of Statistics but instead its + * instance contains 3 instances of Statistics: + * 1) vmStats + * 2) heapMemStats + * 3) nonHeapMemStats + */ + + Method getProcessStats = getGemFireStatSampler().getClass().getMethod("getProcessStats"); + assertNotNull(getProcessStats); + + ProcessStats processStats = statSampler.getProcessStats(); + if (osName.equals("SunOS")) { + assertNotNull(processStats); + assertTrue(PureJavaMode.osStatsAreAvailable()); + assertTrue(allStats.containsStatisticsType("SolarisProcessStats")); + assertTrue(allStats.containsStatisticsType("SolarisSystemStats")); + } else if (osName.startsWith("Windows")) { + // fails on Windows 7: 45395 "ProcessStats are not created on Windows 7" + assertNotNull("ProcessStats were not created on " + osName, processStats); + assertTrue(PureJavaMode.osStatsAreAvailable()); + assertTrue(allStats.containsStatisticsType("WindowsProcessStats")); + assertTrue(allStats.containsStatisticsType("WindowsSystemStats")); + } else if (osName.startsWith("Linux")) { + assertNotNull(processStats); + assertTrue(PureJavaMode.osStatsAreAvailable()); + assertTrue(allStats.containsStatisticsType("LinuxProcessStats")); + assertTrue(allStats.containsStatisticsType("LinuxSystemStats")); + } else if (osName.equals("Mac OS X")) { + assertNull(processStats); + assertFalse(PureJavaMode.osStatsAreAvailable()); + assertFalse(allStats.containsStatisticsType("OSXProcessStats")); + assertFalse(allStats.containsStatisticsType("OSXSystemStats")); + } else { + assertNull(processStats); + } + + String productDesc = statSampler.getProductDescription(); + assertTrue(productDesc.contains(GemFireVersion.getGemFireVersion())); + assertTrue(productDesc.contains(GemFireVersion.getBuildId())); + assertTrue(productDesc.contains(GemFireVersion.getSourceDate())); + } + + /** + * Tests that the configured archive file is created and exists. + */ + @Test + public void testArchiveFileExists() throws Exception { + final String dir = this.testDir.getAbsolutePath(); + final String archiveFileName = dir + File.separator + this.testName.getMethodName() + ".gfs"; + + final File archiveFile1 = new File(dir + File.separator + this.testName.getMethodName() + ".gfs"); + + Properties props = createGemFireProperties(); + props.setProperty(STATISTIC_ARCHIVE_FILE, archiveFileName); + connect(props); + + GemFireStatSampler statSampler = getGemFireStatSampler(); + assertTrue(statSampler.waitForInitialization(5000)); + + final File archiveFile = statSampler.getArchiveFileName(); + assertNotNull(archiveFile); + assertEquals(archiveFile1, archiveFile); + + waitForFileToExist(archiveFile, 5000, 10); + + assertTrue("File name incorrect: archiveFile.getName()=" + archiveFile.getName() + + " archiveFile.getAbsolutePath()=" + archiveFile.getAbsolutePath() + + " getCanonicalPath()" + archiveFile.getCanonicalPath(), + archiveFileName.contains(archiveFile.getName())); + } + + /** + * Tests the statistics sample rate within an acceptable margin of error. + */ + @Test + public void testSampleRate() throws Exception { + connect(createGemFireProperties()); + + GemFireStatSampler statSampler = getGemFireStatSampler(); + assertTrue(statSampler.waitForInitialization(5000)); + + assertEquals(STAT_SAMPLE_RATE, statSampler.getSampleRate()); + + assertTrue(getStatisticsManager().getStatListModCount() > 0); + + List statistics = getStatisticsManager().getStatsList(); + assertNotNull(statistics); + assertTrue(statistics.size() > 0); + + StatisticsType statSamplerType = getStatisticsManager().findType("StatSampler"); + Statistics[] statsArray = getStatisticsManager().findStatisticsByType(statSamplerType); + assertEquals(1, statsArray.length); + + final Statistics statSamplerStats = statsArray[0]; + final int initialSampleCount = statSamplerStats.getInt("sampleCount"); + final int expectedSampleCount = initialSampleCount + 2; + + waitForExpectedStatValue(statSamplerStats, "sampleCount", expectedSampleCount, 5000, 10); + } + + /** + * Adds a LocalStatListener for an individual stat. Validates that it + * receives notifications. Removes the listener and validates that it + * was in fact removed and no longer receives notifications. + */ + @Test + public void testLocalStatListener() throws Exception { + connect(createGemFireProperties()); + + GemFireStatSampler statSampler = getGemFireStatSampler(); + assertTrue(statSampler.waitForInitialization(5000)); + + Method getLocalListeners = getGemFireStatSampler().getClass().getMethod("getLocalListeners"); + assertNotNull(getLocalListeners); + + Method addLocalStatListener = getGemFireStatSampler().getClass().getMethod("addLocalStatListener", LocalStatListener.class, Statistics.class, String.class); + assertNotNull(addLocalStatListener); + + Method removeLocalStatListener = getGemFireStatSampler().getClass().getMethod("removeLocalStatListener", LocalStatListener.class); + assertNotNull(removeLocalStatListener); + + // validate that there are no listeners + assertTrue(statSampler.getLocalListeners().isEmpty()); + + // add a listener for sampleCount stat in StatSampler statistics + StatisticsType statSamplerType = getStatisticsManager().findType("StatSampler"); + Statistics[] statsArray = getStatisticsManager().findStatisticsByType(statSamplerType); + assertEquals(1, statsArray.length); + + final Statistics statSamplerStats = statsArray[0]; + final String statName = "sampleCount"; + final AtomicInteger sampleCountValue = new AtomicInteger(0); + final AtomicInteger sampleCountChanged = new AtomicInteger(0); + + LocalStatListener listener = new LocalStatListener() { + public void statValueChanged(double value) { + sampleCountValue.set((int)value); + sampleCountChanged.incrementAndGet(); + } + }; + + statSampler.addLocalStatListener(listener, statSamplerStats, statName); + assertTrue(statSampler.getLocalListeners().size() == 1); + + // there's a level of indirection here and some protected member fields + LocalStatListenerImpl lsli = (LocalStatListenerImpl) + statSampler.getLocalListeners().iterator().next(); + assertEquals("sampleCount", lsli.stat.getName()); + + // wait for the listener to update 4 times + final int expectedChanges = 4; + boolean done = false; + try { + for (StopWatch time = new StopWatch(true); !done && time.elapsedTimeMillis() < 5000; done = (sampleCountChanged.get() >= expectedChanges)) { + Thread.sleep(10); + } + } catch (InterruptedException e) { + Thread.currentThread().interrupt(); + } + assertTrue("Waiting for sampleCountChanged >= " + expectedChanges, done); + + // validate that the listener fired and updated the value + assertTrue(sampleCountValue.get() > 0); + assertTrue(sampleCountChanged.get() >= expectedChanges); + + // remove the listener + statSampler.removeLocalStatListener(listener); + final int expectedSampleCountValue = sampleCountValue.get(); + final int expectedSampleCountChanged = sampleCountChanged.get(); + + // validate that there are no listeners now + assertTrue(statSampler.getLocalListeners().isEmpty()); + + // wait for 2 stat samples to occur + waitForStatSample(statSamplerStats, expectedSampleCountValue, 5000, 10); + + // validate that the listener did not fire + assertEquals(expectedSampleCountValue, sampleCountValue.get()); + assertEquals(expectedSampleCountChanged, sampleCountChanged.get()); + } + + /** + * Invokes stop() and then validates that the sampler did in fact stop. + */ + @Test + public void testStop() throws Exception { + connect(createGemFireProperties()); + + GemFireStatSampler statSampler = getGemFireStatSampler(); + assertTrue(statSampler.waitForInitialization(5000)); + + // validate the stat sampler is running + StatisticsType statSamplerType = getStatisticsManager().findType("StatSampler"); + Statistics[] statsArray = getStatisticsManager().findStatisticsByType(statSamplerType); + assertEquals(1, statsArray.length); + + final Statistics statSamplerStats = statsArray[0]; + final int initialSampleCount = statSamplerStats.getInt("sampleCount"); + final int expectedSampleCount = initialSampleCount + 2; + + waitForStatSample(statSamplerStats, expectedSampleCount, 20000, 10); + + // stop the stat sampler + statSampler.stop(); + + // validate the stat sampler has stopped + final int stoppedSampleCount = statSamplerStats.getInt("sampleCount"); + + // the following should timeout rather than complete + assertStatValueDoesNotChange(statSamplerStats, "sampleCount", stoppedSampleCount, 5000, 10); + + assertEquals(stoppedSampleCount, statSamplerStats.getInt("sampleCount")); + } + + /** + * Verifies that archive rolling works correctly when archive-file-size-limit + * is specified. + */ + @Test + public void testArchiveRolling() throws Exception { + final String dirName = this.testDir.getAbsolutePath() + File.separator + this.testName; + new File(dirName).mkdirs(); + final String archiveFileName = dirName + File.separator + this.testName + ".gfs"; + + final File archiveFile = new File(archiveFileName); + final File archiveFile1 = new File(dirName + File.separator + this.testName + "-01-01.gfs"); + final File archiveFile2 = new File(dirName + File.separator + this.testName + "-01-02.gfs"); + final File archiveFile3 = new File(dirName + File.separator + this.testName + "-01-03.gfs"); + + // set the system property to use KB instead of MB for file size + System.setProperty(HostStatSampler.TEST_FILE_SIZE_LIMIT_IN_KB_PROPERTY, "true"); + Properties props = createGemFireProperties(); + props.setProperty(ARCHIVE_FILE_SIZE_LIMIT, "1"); + props.setProperty(ARCHIVE_DISK_SPACE_LIMIT, "0"); + props.setProperty(STATISTIC_ARCHIVE_FILE, archiveFileName); + connect(props); + + assertTrue(getGemFireStatSampler().waitForInitialization(5000)); + + boolean done = false; + try { + for (StopWatch time = new StopWatch(true); !done && time.elapsedTimeMillis() < 4000; done = (getSampleCollector() != null && getSampleCollector().getStatArchiveHandler() != null)) { + Thread.sleep(10); + } + } catch (InterruptedException e) { + Thread.currentThread().interrupt(); + } + assertTrue("Waiting for getSampleCollector().getStatArchiveHandler() to not be null", done); + + StatArchiveHandler statArchiveHandler = getSampleCollector().getStatArchiveHandler(); + StatArchiveHandlerConfig config = statArchiveHandler.getStatArchiveHandlerConfig(); + assertEquals(1 * 1024, config.getArchiveFileSizeLimit()); + + waitForFileToExist(archiveFile, 4000, 10); + waitForFileToExist(archiveFile1, 4000, 10); + waitForFileToExist(archiveFile2, 4000, 10); + waitForFileToExist(archiveFile3, 4000, 10); + } + + /** + * Verifies that archive removal works correctly when archive-disk-space-limit + * is specified. + */ + @Test + public void testArchiveRemoval() throws Exception { + final String dirName = this.testDir.getAbsolutePath();// + File.separator + this.testName; + new File(dirName).mkdirs(); + final String archiveFileName = dirName + File.separator + this.testName + ".gfs"; + + final File archiveFile = new File(archiveFileName); + final File archiveFile1 = new File(dirName + File.separator + this.testName + "-01-01.gfs"); + final File archiveFile2 = new File(dirName + File.separator + this.testName + "-01-02.gfs"); + final File archiveFile3 = new File(dirName + File.separator + this.testName + "-01-03.gfs"); + final File archiveFile4 = new File(dirName + File.separator + this.testName + "-01-04.gfs"); + + final int sampleRate = 1000; + + // set the system property to use KB instead of MB for file size + System.setProperty(HostStatSampler.TEST_FILE_SIZE_LIMIT_IN_KB_PROPERTY, "true"); + Properties props = createGemFireProperties(); + props.setProperty(STATISTIC_ARCHIVE_FILE, archiveFileName); + props.setProperty(ARCHIVE_FILE_SIZE_LIMIT, "1"); + props.setProperty(ARCHIVE_DISK_SPACE_LIMIT, "12"); + props.setProperty(STATISTIC_SAMPLE_RATE, String.valueOf(sampleRate)); + connect(props); + + assertTrue(getGemFireStatSampler().waitForInitialization(5000)); + + boolean exists1 = false; + boolean exists2 = false; + boolean exists3 = false; + boolean exists4 = false; + boolean exists = false; + boolean done = false; + try { + for (StopWatch time = new StopWatch(true); !done && time.elapsedTimeMillis() < 10*sampleRate;) { + exists1 = exists1 || archiveFile1.exists(); + exists2 = exists2 || archiveFile2.exists(); + exists3 = exists3 || archiveFile3.exists(); + exists4 = exists4 || archiveFile4.exists(); + exists = exists || archiveFile.exists(); + done = exists1 && exists2 && exists3 && exists4 && exists; + if (!done) { + Thread.sleep(10); + } + } + } catch (InterruptedException e) { + Thread.currentThread().interrupt(); + } + assertTrue("Waiting for archive files to exist:" + + " exists1=" + exists1 + + " exists2=" + exists2 + + " exists3=" + exists3 + + " exists4=" + exists4 + + " exists=" + exists, done); + + waitForFileToDelete(archiveFile1, 10*sampleRate, 10); + } + + @Test + public void testLocalStatListenerRegistration() throws Exception { + connect(createGemFireProperties()); + + final GemFireStatSampler statSampler = getGemFireStatSampler(); + statSampler.waitForInitialization(5000); + + final AtomicBoolean flag = new AtomicBoolean(false); + final LocalStatListener listener = new LocalStatListener(){ + public void statValueChanged(double value) { + flag.set(true); + } + }; + + final String tenuredPoolName = HeapMemoryMonitor.getTenuredMemoryPoolMXBean().getName(); + logger.info("TenuredPoolName: {}", tenuredPoolName); + + final List list = ((StatisticsManager)this.system).getStatsList(); + assertFalse(list.isEmpty()); + + boolean done = false; + try { + for (StopWatch time = new StopWatch(true); !done && time.elapsedTimeMillis() < 5000;) { + Thread.sleep(10); + int i=0; + synchronized (list) { + for (Object obj : list) { + ++i; + logger.info("List:{}:{}", i, obj); + if (obj instanceof StatisticsImpl) { + StatisticsImpl si = (StatisticsImpl)obj; + logger.info("stat:{}", si.getTextId()); + if (si.getTextId().contains(tenuredPoolName)) { + statSampler.addLocalStatListener(listener, si, "currentUsedMemory"); + done = true; + } + } + } + } + //done = false; + } + } catch (InterruptedException e) { + Thread.currentThread().interrupt(); + } + assertTrue("Waiting for " + tenuredPoolName + " statistics to be added to create listener for", done); + + assertTrue("expected at least one stat listener, found " + + statSampler.getLocalListeners().size(), + statSampler.getLocalListeners().size() > 0); + + long maxTenuredMemory = HeapMemoryMonitor.getTenuredMemoryPoolMXBean() + .getUsage().getMax(); + + //byte[] bytes = new byte[1024 * 1024 * 10]; + byte[] bytes = new byte[(int)(maxTenuredMemory*0.01)]; + Arrays.fill(bytes, Byte.MAX_VALUE); + + done = false; + try { + for (StopWatch time = new StopWatch(true); !done && time.elapsedTimeMillis() < 5000; done = (flag.get())) { + Thread.sleep(10); + } + } catch (InterruptedException e) { + Thread.currentThread().interrupt(); + } + assertTrue("Waiting for listener to set flag to true", done); + } + + @Override + protected StatisticsManager getStatisticsManager() { + return (InternalDistributedSystem)this.system; + } + + protected OsStatisticsFactory getOsStatisticsFactory() { + return (InternalDistributedSystem)this.system; + } + + private GemFireStatSampler getGemFireStatSampler() { + return ((InternalDistributedSystem)this.system).getStatSampler(); + } + + private SampleCollector getSampleCollector() { + return getGemFireStatSampler().getSampleCollector(); + } + + private Properties createGemFireProperties() { + Properties props = new Properties(); + props.setProperty(STATISTIC_SAMPLING_ENABLED, "true"); // TODO: test true/false + props.setProperty(ENABLE_TIME_STATISTICS, "true"); // TODO: test true/false + props.setProperty(STATISTIC_SAMPLE_RATE, String.valueOf(STAT_SAMPLE_RATE)); + props.setProperty(ARCHIVE_FILE_SIZE_LIMIT, "0"); + props.setProperty(ARCHIVE_DISK_SPACE_LIMIT, "0"); + props.setProperty(MCAST_PORT, "0"); + props.setProperty(LOCATORS, ""); + return props; + } + + /** + * Creates a fresh loner DistributedSystem for each test. Note + * that the DistributedSystem is the StatisticsManager/Factory/etc. + */ + @SuppressWarnings("deprecation") + private void connect(Properties props) { + this.system = DistributedSystem.connect(props); + } + + @SuppressWarnings("deprecation") + private void disconnect() { + if (this.system != null) { + this.system.disconnect(); + this.system = null; + } + } + + // public static class AsyncInvoker { + // public static AsyncInvocation invokeAsync(Runnable r) { + // return invokeAsync(r, "run", new Object[0]); + // } + // public static AsyncInvocation invokeAsync(Callable c) { + // return invokeAsync(c, "call", new Object[0]); + // } + // public static AsyncInvocation invokeAsync( + // final Object o, final String methodName, final Object[] args) { + // AsyncInvocation ai = + // new AsyncInvocation(o, methodName, new Runnable() { + // public void run() { + // MethExecutorResult result = + // MethExecutor.executeObject(o, methodName, args); + // if (result.exceptionOccurred()) { + // throw new AsyncInvocationException(result.getException()); + // } + // AsyncInvocation.setReturnValue(result.getResult()); + // } + // }); + // ai.start(); + // return ai; + // } + // + // public static class AsyncInvocationException extends RuntimeException { + // private static final long serialVersionUID = -5522299018650622945L; + // /** + // * Creates a new AsyncInvocationException. + // */ + // public AsyncInvocationException(String message) { + // super(message); + // } + // + // /** + // * Creates a new AsyncInvocationException that was + // * caused by a given exception + // */ + // public AsyncInvocationException(String message, Throwable thr) { + // super(message, thr); + // } + // + // /** + // * Creates a new AsyncInvocationException that was + // * caused by a given exception + // */ + // public AsyncInvocationException(Throwable thr) { + // super(thr.getMessage(), thr); + // } + // } + // } + } http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/dfbc88b2/geode-core/src/test/java/com/gemstone/gemfire/internal/statistics/SimpleStatSamplerIntegrationTest.java ---------------------------------------------------------------------- diff --cc geode-core/src/test/java/com/gemstone/gemfire/internal/statistics/SimpleStatSamplerIntegrationTest.java index 0000000,d86b968..f3b80a7 mode 000000,100755..100755 --- a/geode-core/src/test/java/com/gemstone/gemfire/internal/statistics/SimpleStatSamplerIntegrationTest.java +++ b/geode-core/src/test/java/com/gemstone/gemfire/internal/statistics/SimpleStatSamplerIntegrationTest.java @@@ -1,0 -1,351 +1,351 @@@ + /* + * 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 com.gemstone.gemfire.internal.statistics; + + import static org.junit.Assert.*; + + import java.io.File; + import java.lang.reflect.Method; + import java.util.List; + + import org.junit.After; + import org.junit.Assert; + import org.junit.Before; + import org.junit.Rule; + import org.junit.Test; + import org.junit.experimental.categories.Category; + import org.junit.rules.TemporaryFolder; + import org.junit.rules.TestName; + + import com.gemstone.gemfire.CancelCriterion; + import com.gemstone.gemfire.Statistics; + import com.gemstone.gemfire.StatisticsType; -import com.gemstone.gemfire.internal.SocketCreator; ++import com.gemstone.gemfire.internal.net.SocketCreator; + import com.gemstone.gemfire.internal.stats50.VMStats50; + import com.gemstone.gemfire.test.junit.categories.IntegrationTest; + + /** + * Integration tests for {@link SimpleStatSampler}. + * + * @since GemFire 7.0 + */ + @Category(IntegrationTest.class) + public class SimpleStatSamplerIntegrationTest extends StatSamplerTestCase { + + private LocalStatisticsFactory statisticsFactory; + private File testDir; + + @Rule + public TemporaryFolder temporaryFolder = new TemporaryFolder(); + + @Rule + public TestName testName = new TestName(); + + @Before + public void setUp() throws Exception { + this.testDir = this.temporaryFolder.getRoot(); + assertTrue(this.testDir.exists()); + System.setProperty(SimpleStatSampler.ARCHIVE_FILE_NAME_PROPERTY, + this.testDir.getAbsolutePath() + File.separator + SimpleStatSampler.DEFAULT_ARCHIVE_FILE_NAME); + } + + @After + public void tearDown() throws Exception { + System.clearProperty(SimpleStatSampler.ARCHIVE_FILE_NAME_PROPERTY); + System.clearProperty(SimpleStatSampler.FILE_SIZE_LIMIT_PROPERTY); + System.clearProperty(SimpleStatSampler.DISK_SPACE_LIMIT_PROPERTY); + System.clearProperty(SimpleStatSampler.SAMPLE_RATE_PROPERTY); + closeStatisticsFactory(); + } + + /** + * Tests the majority of getters and the basic functionality of the sampler. + */ + @Test + public void testBasics() throws Exception { + initStatisticsFactory(); + + SimpleStatSampler statSampler = getSimpleStatSampler(); + assertTrue(statSampler.waitForInitialization(5000)); + + assertEquals(new File(System.getProperty(SimpleStatSampler.ARCHIVE_FILE_NAME_PROPERTY)), + statSampler.getArchiveFileName()); + assertEquals(0, statSampler.getArchiveFileSizeLimit()); + assertEquals(0, statSampler.getArchiveDiskSpaceLimit()); + assertEquals(SimpleStatSampler.DEFAULT_SAMPLE_RATE, statSampler.getSampleRate()); + assertEquals(true, statSampler.isSamplingEnabled()); + + int statsCount = statSampler.getStatisticsManager().getStatisticsCount(); + + assertEquals(statsCount, statSampler.getStatisticsModCount()); + assertEquals(statsCount, statSampler.getStatisticsManager().getStatisticsCount()); + assertEquals(statsCount, statSampler.getStatistics().length); + + assertTrue(statsCount > 0); + + Assert.assertEquals(getStatisticsManager().getId(), statSampler.getSystemId()); + assertTrue(statSampler.getSystemStartTime() <= System.currentTimeMillis()); - Assert.assertEquals(SocketCreator.getHostName(SocketCreator.getLocalHost()), ++ assertEquals(SocketCreator.getHostName(SocketCreator.getLocalHost()), + statSampler.getSystemDirectoryPath()); + + VMStatsContract vmStats = statSampler.getVMStats(); + assertNotNull(vmStats); + assertTrue(vmStats instanceof VMStats50); + /* NOTE: VMStats50 is not an instance of Statistics but instead its + * instance contains 3 instances of Statistics: + * 1) vmStats + * 2) heapMemStats + * 3) nonHeapMemStats + */ + + Method getProcessStats = null; + try { + getProcessStats = SimpleStatSampler.class.getMethod("getProcessStats"); + fail("SimpleStatSampler should not have the method getProcessStats()"); + } catch (NoSuchMethodException exected) { + // passed + } + assertNull(getProcessStats); + + assertEquals("Unknown product", statSampler.getProductDescription()); + } + + /** + * Tests that the configured archive file is created and exists. + */ + @Test + public void testArchiveFileExists() throws Exception { + final String dir = this.testDir.getAbsolutePath(); + final String archiveFileName = dir + File.separator + this.testName + ".gfs"; + final File archiveFile1 = new File(dir + File.separator + this.testName + ".gfs"); + System.setProperty(SimpleStatSampler.ARCHIVE_FILE_NAME_PROPERTY, archiveFileName); + initStatisticsFactory(); + + SimpleStatSampler statSampler = getSimpleStatSampler(); + assertTrue(statSampler.waitForInitialization(5000)); + + final File archiveFile = statSampler.getArchiveFileName(); + assertNotNull(archiveFile); + assertEquals(archiveFile1, archiveFile); + + waitForFileToExist(archiveFile, 5000, 10); + + assertTrue("File name incorrect: archiveFile.getName()=" + archiveFile.getName() + + " archiveFile.getAbsolutePath()=" + archiveFile.getAbsolutePath() + + " getCanonicalPath()" + archiveFile.getCanonicalPath(), + archiveFileName.contains(archiveFile.getName())); + } + + /** + * Tests the statistics sample rate within an acceptable margin of error. + */ + @Test + public void testSampleRate() throws Exception { + initStatisticsFactory(); + + SimpleStatSampler statSampler = getSimpleStatSampler(); + assertTrue(statSampler.waitForInitialization(5000)); + + assertEquals(SimpleStatSampler.DEFAULT_SAMPLE_RATE, statSampler.getSampleRate()); + + assertTrue(getStatisticsManager().getStatListModCount() > 0); + + List statistics = getStatisticsManager().getStatsList(); + assertNotNull(statistics); + assertTrue(statistics.size() > 0); + + StatisticsType statSamplerType = getStatisticsManager().findType("StatSampler"); + Statistics[] statsArray = getStatisticsManager().findStatisticsByType(statSamplerType); + assertEquals(1, statsArray.length); + + final Statistics statSamplerStats = statsArray[0]; + final int initialSampleCount = statSamplerStats.getInt("sampleCount"); + final int expectedSampleCount = initialSampleCount + 2; + + waitForStatSample(statSamplerStats, expectedSampleCount, 20000, 10); + } + + /** + * Tests lack of methods for supporting LocalStatListener. + */ + @Test + public void testLocalStatListener() throws Exception { + initStatisticsFactory(); + + SimpleStatSampler statSampler = getSimpleStatSampler(); + assertTrue(statSampler.waitForInitialization(5000)); + + Method getLocalListeners = null; + try { + getLocalListeners = getSimpleStatSampler().getClass().getMethod("getLocalListeners"); + fail("SimpleStatSampler should not have the method getLocalListeners()"); + } catch (NoSuchMethodException exected) { + // passed + } + assertNull(getLocalListeners); + + Method addLocalStatListener = null; + try { + addLocalStatListener = getSimpleStatSampler().getClass().getMethod("addLocalStatListener", LocalStatListener.class, Statistics.class, String.class); + fail("SimpleStatSampler should not have the method addLocalStatListener()"); + } catch (NoSuchMethodException exected) { + // passed + } + assertNull(addLocalStatListener); + + Method removeLocalStatListener = null; + try { + removeLocalStatListener = getSimpleStatSampler().getClass().getMethod("removeLocalStatListener", LocalStatListener.class); + fail("SimpleStatSampler should not have the method addLocalStatListener()"); + } catch (NoSuchMethodException exected) { + // passed + } + assertNull(removeLocalStatListener); + } + + /** + * Invokes stop() and then validates that the sampler did in fact stop. + */ + @Test + public void testStop() throws Exception { + initStatisticsFactory(); + + SimpleStatSampler statSampler = getSimpleStatSampler(); + assertTrue(statSampler.waitForInitialization(5000)); + + // validate the stat sampler is running + StatisticsType statSamplerType = getStatisticsManager().findType("StatSampler"); + Statistics[] statsArray = getStatisticsManager().findStatisticsByType(statSamplerType); + assertEquals(1, statsArray.length); + + final Statistics statSamplerStats = statsArray[0]; + final int initialSampleCount = statSamplerStats.getInt("sampleCount"); + final int expectedSampleCount = initialSampleCount + 2; + + waitForStatSample(statSamplerStats, expectedSampleCount, 20000, 10); + + // stop the stat sampler + statSampler.stop(); + + // validate the stat sampler has stopped + final int stoppedSampleCount = statSamplerStats.getInt("sampleCount"); + + // the following should timeout without completing + assertStatValueDoesNotChange(statSamplerStats, "sampleCount", stoppedSampleCount, 5000, 10); + + assertEquals(stoppedSampleCount, statSamplerStats.getInt("sampleCount")); + } + + /** + * Verifies that archive rolling works correctly when archive-file-size-limit + * is specified. This feature is broken in SimpleStatSampler. + */ + @Test + public void testArchiveRolling() throws Exception { + // set the system property to use KB instead of MB for file size + System.setProperty(HostStatSampler.TEST_FILE_SIZE_LIMIT_IN_KB_PROPERTY, "true"); + + final String dir = this.testDir.getAbsolutePath() + File.separator + this.testName; + new File(dir).mkdir(); + + final String archiveFileName = dir + File.separator + this.testName + ".gfs"; + System.setProperty(SimpleStatSampler.ARCHIVE_FILE_NAME_PROPERTY, archiveFileName); + System.setProperty(SimpleStatSampler.FILE_SIZE_LIMIT_PROPERTY, "1"); + System.setProperty(SimpleStatSampler.DISK_SPACE_LIMIT_PROPERTY, "0"); + System.setProperty(SimpleStatSampler.SAMPLE_RATE_PROPERTY, "1000"); + initStatisticsFactory(); + + final File archiveFile1 = new File(dir + File.separator + this.testName + "-01-01.gfs"); + final File archiveFile2 = new File(dir + File.separator + this.testName + "-01-02.gfs"); + final File archiveFile3 = new File(dir + File.separator + this.testName + "-01-03.gfs"); + final File archiveFile4 = new File(dir + File.separator + this.testName + "-01-04.gfs"); + + assertTrue(getSimpleStatSampler().waitForInitialization(5000)); + + assertTrue(getSimpleStatSampler().fileSizeLimitInKB()); + assertEquals(1024, getSimpleStatSampler().getArchiveFileSizeLimit()); + + waitForFileToExist(archiveFile1, 4000, 10); + waitForFileToExist(archiveFile2, 4000, 10); + waitForFileToExist(archiveFile3, 4000, 10); + waitForFileToExist(archiveFile4, 4000, 10); + } + + /** + * Verifies that archive removal works correctly when archive-disk-space-limit + * is specified. This feature is broken in SimpleStatSampler. + */ + @Test + public void testArchiveRemoval() throws Exception { + // set the system property to use KB instead of MB for file size + System.setProperty(HostStatSampler.TEST_FILE_SIZE_LIMIT_IN_KB_PROPERTY, "true"); + + final String dir = this.testDir.getAbsolutePath() + File.separator + this.testName; + new File(dir).mkdir(); + + final String archiveFileName = dir + File.separator + this.testName + ".gfs"; + final int sampleRate = 1000; + System.setProperty(SimpleStatSampler.ARCHIVE_FILE_NAME_PROPERTY, archiveFileName); + System.setProperty(SimpleStatSampler.FILE_SIZE_LIMIT_PROPERTY, "1"); + System.setProperty(SimpleStatSampler.DISK_SPACE_LIMIT_PROPERTY, "12"); + System.setProperty(SimpleStatSampler.SAMPLE_RATE_PROPERTY, String.valueOf(sampleRate)); + initStatisticsFactory(); + + final File archiveFile1 = new File(dir + File.separator + this.testName + "-01-01.gfs"); + final File archiveFile2 = new File(dir + File.separator + this.testName + "-01-02.gfs"); + final File archiveFile3 = new File(dir + File.separator + this.testName + "-01-03.gfs"); + final File archiveFile4 = new File(dir + File.separator + this.testName + "-01-04.gfs"); + final File archiveFile5 = new File(dir + File.separator + this.testName + "-01-05.gfs"); + + assertTrue(getSimpleStatSampler().waitForInitialization(5000)); + + waitForFileToExist(archiveFile1, 4*sampleRate, 10); + waitForFileToExist(archiveFile2, 4*sampleRate, 10); + waitForFileToExist(archiveFile3, 4*sampleRate, 10); + waitForFileToExist(archiveFile4, 4*sampleRate, 10); + waitForFileToExist(archiveFile5, 4*sampleRate, 10); + waitForFileToDelete(archiveFile1, 10*sampleRate, 10); + } + + @Override + protected StatisticsManager getStatisticsManager() { + return this.statisticsFactory; + } + + private SimpleStatSampler getSimpleStatSampler() { + return this.statisticsFactory.getStatSampler(); + } + + private void initStatisticsFactory() { + CancelCriterion stopper = new CancelCriterion() { + public String cancelInProgress() { + return null; + } + public RuntimeException generateCancelledException(Throwable e) { + return null; + } + }; + this.statisticsFactory = new LocalStatisticsFactory(stopper); + } + + private void closeStatisticsFactory() { + if (this.statisticsFactory != null) { + this.statisticsFactory.close(); + this.statisticsFactory = null; + } + } + } http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/dfbc88b2/geode-core/src/test/resources/com/gemstone/gemfire/codeAnalysis/excludedClasses.txt ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/dfbc88b2/geode-wan/src/main/java/com/gemstone/gemfire/cache/client/internal/locator/wan/LocatorDiscovery.java ---------------------------------------------------------------------- diff --cc geode-wan/src/main/java/com/gemstone/gemfire/cache/client/internal/locator/wan/LocatorDiscovery.java index a9de5b3,0fd206e..4ff2b5e --- a/geode-wan/src/main/java/com/gemstone/gemfire/cache/client/internal/locator/wan/LocatorDiscovery.java +++ b/geode-wan/src/main/java/com/gemstone/gemfire/cache/client/internal/locator/wan/LocatorDiscovery.java @@@ -60,13 -57,12 +60,13 @@@ public class LocatorDiscovery public static final int WAN_LOCATOR_PING_INTERVAL = Integer.getInteger( "WANLocator.PING_INTERVAL", 10000).intValue(); - public LocatorDiscovery(WanLocatorDiscoverer discoverer, DistributionLocatorId locotor,RemoteLocatorJoinRequest request, + public LocatorDiscovery(WanLocatorDiscoverer discoverer, DistributionLocatorId locator,RemoteLocatorJoinRequest request, LocatorMembershipListener locatorListener) { this.discoverer = discoverer; - this.locatorId = locotor; + this.locatorId = locator; this.request = request; this.locatorListener = locatorListener; + this.locatorClient = new TcpClient(); } /** http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/dfbc88b2/geode-wan/src/test/java/com/gemstone/gemfire/internal/cache/wan/WANTestBase.java ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/incubator-geode/blob/dfbc88b2/geode-wan/src/test/java/com/gemstone/gemfire/management/internal/configuration/ClusterConfigurationDUnitTest.java ----------------------------------------------------------------------