package org.infinispan.client.hotrod;
import static org.infinispan.server.hotrod.test.HotRodTestingUtil.hotRodCacheConfiguration;
import static org.testng.AssertJUnit.assertEquals;
import static org.testng.AssertJUnit.assertNotNull;
import static org.testng.AssertJUnit.assertNull;
import static org.testng.AssertJUnit.assertTrue;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.concurrent.TimeUnit;
import org.infinispan.client.hotrod.test.HotRodClientTestingUtil;
import org.infinispan.configuration.cache.ConfigurationBuilder;
import org.infinispan.manager.EmbeddedCacheManager;
import org.infinispan.server.hotrod.HotRodServer;
import org.infinispan.test.SingleCacheManagerTest;
import org.infinispan.test.fwk.TestCacheManagerFactory;
import org.infinispan.util.logging.Log;
import org.infinispan.util.logging.LogFactory;
import org.testng.annotations.AfterClass;
import org.testng.annotations.Test;
/**
* @author Tristan Tarrant
* @since 9.0
*/
@Test(testName = "client.hotrod.StreamingOpsTest", groups = "functional")
public class StreamingOpsTest extends SingleCacheManagerTest {
private static final Log log = LogFactory.getLog(StreamingOpsTest.class);
private static final String CACHE_NAME = "theCache";
private static final int V1_SIZE = 2_000;
private static final int V2_SIZE = 1_000;
RemoteCache<String, byte[]> remoteCache;
StreamingRemoteCache<String> streamingRemoteCache;
private RemoteCacheManager remoteCacheManager;
protected HotRodServer hotrodServer;
@Override
protected EmbeddedCacheManager createCacheManager() throws Exception {
ConfigurationBuilder builder = hotRodCacheConfiguration(
getDefaultStandaloneCacheConfig(false));
EmbeddedCacheManager cm = TestCacheManagerFactory
.createCacheManager(hotRodCacheConfiguration());
cm.defineConfiguration(CACHE_NAME, builder.build());
cm.getCache(CACHE_NAME);
return cm;
}
@Override
protected void setup() throws Exception {
super.setup();
//pass the config file to the cache
hotrodServer = HotRodClientTestingUtil.startHotRodServer(cacheManager);
log.info("Started server on port: " + hotrodServer.getPort());
remoteCacheManager = getRemoteCacheManager();
remoteCache = remoteCacheManager.getCache(CACHE_NAME);
streamingRemoteCache = remoteCache.streaming();
}
protected RemoteCacheManager getRemoteCacheManager() {
org.infinispan.client.hotrod.configuration.ConfigurationBuilder clientBuilder =
new org.infinispan.client.hotrod.configuration.ConfigurationBuilder();
clientBuilder.addServer().host("localhost").port(hotrodServer.getPort());
return new RemoteCacheManager(clientBuilder.build());
}
@AfterClass
public void testDestroyRemoteCacheFactory() {
HotRodClientTestingUtil.killRemoteCacheManager(remoteCacheManager);
HotRodClientTestingUtil.killServers(hotrodServer);
}
private void consumeAndCloseStream(InputStream is) throws Exception {
if (is != null) {
try {
while (is.read() >= 0) {
//consume
}
} finally {
is.close();
}
}
}
private void writeDataToStream(OutputStream os, int length) throws Exception {
for (int i = 0; i < length; i++) {
os.write(i % 256);
}
}
public void testPutGetStream() throws Exception {
OutputStream k1os = streamingRemoteCache.put("k1");
writeDataToStream(k1os, V1_SIZE);
k1os.close();
InputStream k1is = streamingRemoteCache.get("k1");
int count = readAndCheckDataFromStream(k1is);
assertEquals(V1_SIZE, count);
}
private int readAndCheckDataFromStream(InputStream k1is) throws IOException {
int count = 0;
try {
for (int b = k1is.read(); b >= 0; b = k1is.read(), count++) {
assertEquals(count % 256, b);
}
} finally {
k1is.close();
}
return count;
}
public void testGetStreamWithMetadata() throws Exception {
InputStream k1is = streamingRemoteCache.get("k1");
assertNull("expected null but received a stream", k1is);
consumeAndCloseStream(k1is);
OutputStream k1os = streamingRemoteCache.put("k1");
writeDataToStream(k1os, V1_SIZE);
k1os.close();
k1is = streamingRemoteCache.get("k1");
assertNotNull("expected a stream but received null", k1is);
VersionedMetadata k1metadata = (VersionedMetadata) k1is;
assertEquals(-1, k1metadata.getLifespan());
assertEquals(-1, k1metadata.getMaxIdle());
consumeAndCloseStream(k1is);
k1os = streamingRemoteCache.put("k1", 5, TimeUnit.MINUTES);
writeDataToStream(k1os, V1_SIZE);
k1os.close();
k1is = streamingRemoteCache.get("k1");
assertNotNull("expected a stream but received null", k1is);
k1metadata = (VersionedMetadata) k1is;
assertEquals(TimeUnit.MINUTES.toSeconds(5), k1metadata.getLifespan());
assertEquals(-1, k1metadata.getMaxIdle());
consumeAndCloseStream(k1is);
k1os = streamingRemoteCache.put("k1", 5, TimeUnit.MINUTES, 3, TimeUnit.MINUTES);
writeDataToStream(k1os, V1_SIZE);
k1os.close();
k1is = streamingRemoteCache.get("k1");
assertNotNull("expected a stream but received null", k1is);
k1metadata = (VersionedMetadata) k1is;
assertEquals(TimeUnit.MINUTES.toSeconds(5), k1metadata.getLifespan());
assertEquals(TimeUnit.MINUTES.toSeconds(3), k1metadata.getMaxIdle());
consumeAndCloseStream(k1is);
}
public void testPutIfAbsentStream() throws Exception {
InputStream k1is = streamingRemoteCache.get("k1");
assertNull("expected null but received a stream", k1is);
consumeAndCloseStream(k1is);
// Write a V1 value
OutputStream k1os = streamingRemoteCache.putIfAbsent("k1");
writeDataToStream(k1os, V1_SIZE);
k1os.close();
k1is = streamingRemoteCache.get("k1");
assertEquals(V1_SIZE, readAndCheckDataFromStream(k1is));
// Attempt to overwrite it with a V2 value
k1os = streamingRemoteCache.putIfAbsent("k1");
writeDataToStream(k1os, V2_SIZE);
k1os.close();
// Check that the value was not replaced
k1is = streamingRemoteCache.get("k1");
assertEquals(V1_SIZE, readAndCheckDataFromStream(k1is));
}
public void testReplaceStream() throws Exception {
// Write a V1 value
OutputStream k1os = streamingRemoteCache.putIfAbsent("k1");
writeDataToStream(k1os, V1_SIZE);
k1os.close();
InputStream k1is = streamingRemoteCache.get("k1");
assertEquals(V1_SIZE, readAndCheckDataFromStream(k1is));
long version = ((VersionedMetadata)k1is).getVersion();
assertTrue("Expected a non-zero version: " + version, version > 0);
// Attempt to overwrite it by using a wrong version
k1os = streamingRemoteCache.replaceWithVersion("k1", version + 1);
writeDataToStream(k1os, V2_SIZE);
k1os.close();
// Check that the value was not replaced
k1is = streamingRemoteCache.get("k1");
assertEquals(V1_SIZE, readAndCheckDataFromStream(k1is));
// Attempt to overwrite it by using the correct version
k1os = streamingRemoteCache.replaceWithVersion("k1", version);
writeDataToStream(k1os, V2_SIZE);
k1os.close();
// Check that the value was replaced
k1is = streamingRemoteCache.get("k1");
assertEquals(V2_SIZE, readAndCheckDataFromStream(k1is));
}
}