diff --git a/src/main/java/redis/embedded/RedisExecProvider.java b/src/main/java/redis/embedded/RedisExecProvider.java index a306222f..ba0265a1 100644 --- a/src/main/java/redis/embedded/RedisExecProvider.java +++ b/src/main/java/redis/embedded/RedisExecProvider.java @@ -2,18 +2,22 @@ import com.google.common.base.Preconditions; import com.google.common.collect.Maps; -import redis.embedded.util.Architecture; -import redis.embedded.util.JarUtil; -import redis.embedded.util.OS; -import redis.embedded.util.OsArchitecture; +import redis.embedded.util.*; import java.io.File; import java.io.IOException; import java.util.Map; +import java.util.regex.Pattern; public class RedisExecProvider { - private final Map executables = Maps.newHashMap(); + private final Map executables = Maps.newHashMap(); + public final static Pattern DEFAULT_REDIS_READY_PATTERN = Pattern.compile( + "(?:The server is now ready to accept connections on port)" + // 3.2.1, 2.8.24 + "|(?:Ready to accept connections)" + // 4.0.2 + "|(?:Sentinel ID is)" + // 3.2.1, 4.0.2 + "|(?:Sentinel runid is)" // 2.8.24 + ); /** * @return a new RedisExecProvider instance @@ -33,10 +37,10 @@ private RedisExecProvider() { } private void initExecutables() { - executables.put(OsArchitecture.UNIX_x86_64, "redis-server-3.0.7"); + executables.put(OsArchitecture.UNIX_x86_64, new RedisExecutable("redis-server-3.0.7", DEFAULT_REDIS_READY_PATTERN)); - executables.put(OsArchitecture.MAC_OS_X_x86, "redis-server-3.0.7-darwin"); - executables.put(OsArchitecture.MAC_OS_X_x86_64, "redis-server-3.0.7-darwin"); + executables.put(OsArchitecture.MAC_OS_X_x86, new RedisExecutable("redis-server-3.0.7-darwin", DEFAULT_REDIS_READY_PATTERN)); + executables.put(OsArchitecture.MAC_OS_X_x86_64, new RedisExecutable("redis-server-3.0.7-darwin", DEFAULT_REDIS_READY_PATTERN)); } public RedisExecProvider override(OS os, String executable) { @@ -49,19 +53,30 @@ public RedisExecProvider override(OS os, String executable) { public RedisExecProvider override(OS os, Architecture arch, String executable) { Preconditions.checkNotNull(executable); - executables.put(new OsArchitecture(os, arch), executable); + executables.put(new OsArchitecture(os, arch), new RedisExecutable(executable, DEFAULT_REDIS_READY_PATTERN)); + return this; + } + + public RedisExecProvider override(OS os, Architecture arch, RedisExecutable redisExec) { + Preconditions.checkNotNull(redisExec); + executables.put(new OsArchitecture(os, arch), redisExec); return this; } public File get() throws IOException { OsArchitecture osArch = OsArchitecture.detect(); - String executablePath = executables.get(osArch); + String executablePath = executables.get(osArch).getExecutableName(); return fileExists(executablePath) ? new File(executablePath) : JarUtil.extractExecutableFromJar(executablePath); } + public Pattern getExecutableStartPattern() { + OsArchitecture osArch = OsArchitecture.detect(); + return executables.get(osArch).getStartPattern(); + } + public RedisExecProvider copy() { RedisExecProvider copy = new RedisExecProvider(); diff --git a/src/main/java/redis/embedded/RedisSentinel.java b/src/main/java/redis/embedded/RedisSentinel.java index 3ff42cf1..5961c870 100644 --- a/src/main/java/redis/embedded/RedisSentinel.java +++ b/src/main/java/redis/embedded/RedisSentinel.java @@ -12,16 +12,18 @@ import java.util.regex.Pattern; public class RedisSentinel extends AbstractRedisInstance { - private static final Pattern REDIS_READY_PATTERN = Pattern.compile( - "(?:Sentinel ID is)" + // 3.2.1, 4.0.2 - "|(?:Sentinel runid is)" // 2.8.24 - ); + private Pattern redisReadyPat = RedisExecProvider.DEFAULT_REDIS_READY_PATTERN; public RedisSentinel(List args, int port) { super(port); this.args = new ArrayList<>(args); } + void setRedisReadyPat(Pattern redisReadyPat) { + Preconditions.checkNotNull(redisReadyPat); + this.redisReadyPat = redisReadyPat; + } + @Deprecated public static Builder builder() { return new Builder(); @@ -29,7 +31,7 @@ public static Builder builder() { @Override protected Pattern redisReadyPattern() { - return REDIS_READY_PATTERN; + return redisReadyPat; } @SuppressWarnings("unused") @@ -137,6 +139,7 @@ public RedisSentinel build() { RedisSentinel redisSentinel = new RedisSentinel(args, port); redisSentinel.setLogProcessOutput(logProcessOutput); redisSentinel.setStartupTimeoutMs(startupTimeoutMs); + redisSentinel.setRedisReadyPat(redisExecProvider.getExecutableStartPattern()); return redisSentinel; } diff --git a/src/main/java/redis/embedded/RedisServer.java b/src/main/java/redis/embedded/RedisServer.java index c19a3fe6..3f9ff17a 100644 --- a/src/main/java/redis/embedded/RedisServer.java +++ b/src/main/java/redis/embedded/RedisServer.java @@ -1,5 +1,6 @@ package redis.embedded; +import com.google.common.base.Preconditions; import com.google.common.base.Strings; import com.google.common.io.Files; import redis.embedded.exceptions.RedisBuildingException; @@ -15,10 +16,7 @@ public class RedisServer extends AbstractRedisInstance { - private static final Pattern REDIS_READY_PATTERN = Pattern.compile( - "(?:The server is now ready to accept connections on port)" + // 3.2.1, 2.8.24 - "|(?:Ready to accept connections)" // 4.0.2 - ); + private Pattern redisReadyPat = RedisExecProvider.DEFAULT_REDIS_READY_PATTERN; private static final int DEFAULT_REDIS_PORT = 6379; @@ -37,6 +35,7 @@ public RedisServer(int port) throws IOException { public RedisServer(RedisExecProvider redisExecProvider, int port) throws IOException { super(port); + this.redisReadyPat = redisExecProvider.getExecutableStartPattern(); this.args = Arrays.asList( redisExecProvider.get().getAbsolutePath(), "--port", Integer.toString(port) @@ -48,6 +47,11 @@ public RedisServer(RedisExecProvider redisExecProvider, int port) throws IOExcep this.args = new ArrayList<>(args); } + void setRedisReadyPat(Pattern redisReadyPat) { + Preconditions.checkNotNull(redisReadyPat); + this.redisReadyPat = redisReadyPat; + } + /** * Prefer using {@code new RedisServer.Builder()} directly. * @@ -60,7 +64,7 @@ public static Builder builder() { @Override protected Pattern redisReadyPattern() { - return REDIS_READY_PATTERN; + return redisReadyPat; } @SuppressWarnings("unused") @@ -138,6 +142,7 @@ public RedisServer build() { RedisServer redisServer = new RedisServer(args, port); redisServer.setLogProcessOutput(logProcessOutput); redisServer.setStartupTimeoutMs(startupTimeoutMs); + redisServer.setRedisReadyPat(redisExecProvider.getExecutableStartPattern()); return redisServer; } diff --git a/src/main/java/redis/embedded/util/RedisExecutable.java b/src/main/java/redis/embedded/util/RedisExecutable.java new file mode 100644 index 00000000..f5f4f6d0 --- /dev/null +++ b/src/main/java/redis/embedded/util/RedisExecutable.java @@ -0,0 +1,40 @@ +package redis.embedded.util; + +import java.util.regex.Pattern; + +public class RedisExecutable { + private String executableName; + private Pattern startPattern; + + public RedisExecutable(String exeName, Pattern startPattern) { + this.executableName = exeName; + this.startPattern = startPattern; + } + + public String getExecutableName() { + return executableName; + } + + public Pattern getStartPattern() { + return startPattern; + } + + public String getStartPatternAsString() { + return startPattern.pattern(); + } + + public RedisExecutable copy() { + return new RedisExecutable(executableName, startPattern); + } + + @Override + public boolean equals(Object obj) { + return obj instanceof RedisExecutable && ((RedisExecutable) obj).executableName.contentEquals(executableName) && + ((RedisExecutable)obj).startPattern.pattern().contentEquals(startPattern.pattern()); + } + + @Override + public int hashCode() { + return executableName.hashCode() + startPattern.pattern().hashCode(); + } +}