Last active
March 20, 2019 13:39
-
-
Save rnorth/4c3666d62fa93bf0daa813b282e4ebff to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import com.github.dockerjava.api.command.InspectContainerResponse; | |
import eu.rekawek.toxiproxy.Proxy; | |
import eu.rekawek.toxiproxy.ToxiproxyClient; | |
import eu.rekawek.toxiproxy.model.ToxicDirection; | |
import eu.rekawek.toxiproxy.model.ToxicList; | |
import org.junit.Rule; | |
import org.junit.Test; | |
import org.testcontainers.containers.GenericContainer; | |
import org.testcontainers.containers.Network; | |
import org.testcontainers.containers.wait.strategy.HttpWaitStrategy; | |
import redis.clients.jedis.Jedis; | |
import java.io.IOException; | |
import java.util.HashMap; | |
import java.util.Map; | |
import java.util.concurrent.atomic.AtomicInteger; | |
import static org.junit.Assert.assertEquals; | |
import static org.junit.Assert.fail; | |
public class ToxiProxyTest { | |
@Rule | |
public Network network = Network.newNetwork(); | |
@Rule | |
public GenericContainer redis = new GenericContainer("redis:latest") | |
.withExposedPorts(6379) | |
.withNetwork(network); | |
@Rule | |
public ToxiproxyContainer toxiproxy = new ToxiproxyContainer() | |
.withNetwork(network); | |
@Test | |
public void testDirect() { | |
final Jedis jedis = new Jedis(redis.getContainerIpAddress(), redis.getFirstMappedPort()); | |
jedis.set("Hello", "world"); | |
final String s = jedis.get("Hello"); | |
assertEquals("world", s); | |
} | |
@Test | |
public void testViaProxy() throws IOException { | |
final ToxiproxyContainer.ContainerProxy proxy = toxiproxy.getProxy(redis, 6379); | |
final Jedis jedis = new Jedis(proxy.getContainerIpAddress(), proxy.getProxyPort()); | |
jedis.set("Hello", "world"); | |
String s = jedis.get("Hello"); | |
assertEquals("world", s); | |
proxy.toxics() | |
.latency("latency", ToxicDirection.DOWNSTREAM, 10_000) | |
.setJitter(10_000); | |
for (int i = 0; i < 10; i++) { | |
try { | |
s = jedis.get("Hello"); | |
assertEquals("world", s); | |
return; | |
} catch (Exception e) { | |
} | |
} | |
fail(); | |
} | |
public static class ToxiproxyContainer extends GenericContainer<ToxiproxyContainer> { | |
private ToxiproxyClient client; | |
private final Map<String, ContainerProxy> proxies = new HashMap<>(); | |
private final AtomicInteger nextPort = new AtomicInteger(8666); | |
public ToxiproxyContainer() { | |
super("shopify/toxiproxy:2.1.0"); | |
} | |
@Override | |
protected void configure() { | |
addExposedPorts(8474); | |
setWaitStrategy(new HttpWaitStrategy().forPath("/version").forPort(8474)); | |
for (int i = 0; i < 32; i++) { | |
addExposedPort(8666 + i); | |
} | |
} | |
@Override | |
protected void containerIsStarted(InspectContainerResponse containerInfo) { | |
client = new ToxiproxyClient(getContainerIpAddress(), getMappedPort(8474)); | |
} | |
public ContainerProxy getProxy(GenericContainer container, int port) { | |
String upstream = container.getNetworkAliases().get(0) + ":" + port; | |
return proxies.computeIfAbsent(upstream, __ -> { | |
try { | |
final int toxiPort = nextPort.getAndIncrement(); | |
Proxy proxy = client.createProxy("name", "0.0.0.0:" + toxiPort, upstream); | |
return new ContainerProxy(proxy, getContainerIpAddress(), getMappedPort(toxiPort)); | |
} catch (IOException e) { | |
throw new UnsupportedOperationException(); // TODO: Replace | |
} | |
}); | |
} | |
public static class ContainerProxy { | |
private final Proxy toxi; | |
private final String ip; | |
private final int port; | |
public ContainerProxy(Proxy toxi, String ip, int port) { | |
this.toxi = toxi; | |
this.ip = ip; | |
this.port = port; | |
} | |
public ToxicList toxics() { | |
return toxi.toxics(); | |
} | |
public String getContainerIpAddress() { | |
return ip; | |
} | |
public int getProxyPort() { | |
return port; | |
} | |
} | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment