diff --git a/packages/modules/redis/src/redis-container.test.ts b/packages/modules/redis/src/redis-container.test.ts index 640e523ea..7f4dc5908 100644 --- a/packages/modules/redis/src/redis-container.test.ts +++ b/packages/modules/redis/src/redis-container.test.ts @@ -4,13 +4,13 @@ import { createClient } from "redis"; import { getImage } from "../../../testcontainers/src/utils/test-helper"; import { RedisContainer } from "./redis-container"; -const IMAGE = getImage(__dirname); +const IMAGES = ["redis:6.2.24", "redis:7.4.11", getImage(__dirname)]; const REDISSTACK_IMAGE = getImage(__dirname, 1); -describe("RedisContainer", { timeout: 240_000 }, () => { - it("should connect and execute set-get", async () => { +describe.each(IMAGES)("RedisContainer (%s)", { concurrent: false, timeout: 240_000 }, (image) => { + it.concurrent("should connect and execute set-get", async () => { // redisStartContainer { - await using container = await new RedisContainer(IMAGE).start(); + await using container = await new RedisContainer(image).start(); const client = createClient({ url: container.getConnectionUrl() }); await client.connect(); @@ -22,8 +22,8 @@ describe("RedisContainer", { timeout: 240_000 }, () => { // } }); - it("should connect with password and execute set-get", async () => { - await using container = await new RedisContainer(IMAGE).withPassword("test").start(); + it.concurrent("should connect with password and execute set-get", async () => { + await using container = await new RedisContainer(image).withPassword("test").start(); const client = createClient({ url: container.getConnectionUrl() }); await client.connect(); @@ -34,11 +34,11 @@ describe("RedisContainer", { timeout: 240_000 }, () => { client.destroy(); }); - it("should reconnect with volume and persistence data", async () => { + it.concurrent("should reconnect with volume and persistence data", async () => { // persistentData { const sourcePath = fs.mkdtempSync("redis-"); - await using container = await new RedisContainer(IMAGE).withPassword("test").withPersistence(sourcePath).start(); + await using container = await new RedisContainer(image).withPassword("test").withPersistence(sourcePath).start(); let client = createClient({ url: container.getConnectionUrl() }); await client.connect(); @@ -56,9 +56,9 @@ describe("RedisContainer", { timeout: 240_000 }, () => { // } }); - it("should load initial data and can read it", async () => { + it.concurrent("should load initial data and can read it", async () => { // withPredefinedData { - await using container = await new RedisContainer(IMAGE) + await using container = await new RedisContainer(image) .withPassword("test") .withInitialData(path.join(__dirname, "initData.redis")) .start(); @@ -77,8 +77,8 @@ describe("RedisContainer", { timeout: 240_000 }, () => { // } }); - it("should load initial data once", async () => { - await using container = await new RedisContainer(IMAGE) + it.concurrent("should load initial data once", async () => { + await using container = await new RedisContainer(image) .withInitialData(path.join(__dirname, "initCount.redis")) .start(); @@ -90,11 +90,11 @@ describe("RedisContainer", { timeout: 240_000 }, () => { client.destroy(); }); - it("should start with credentials and login", async () => { + it.concurrent("should start with credentials and login", async () => { // redisStartWithCredentials { const password = "testPassword"; - await using container = await new RedisContainer(IMAGE).withPassword(password).start(); + await using container = await new RedisContainer(image).withPassword(password).start(); expect(container.getConnectionUrl()).toEqual(`redis://:${password}@${container.getHost()}:${container.getPort()}`); // } @@ -108,9 +108,9 @@ describe("RedisContainer", { timeout: 240_000 }, () => { client.destroy(); }); - it("should execute container cmd and return the result", async () => { + it.concurrent("should execute container cmd and return the result", async () => { // executeCommand { - await using container = await new RedisContainer(IMAGE).start(); + await using container = await new RedisContainer(image).start(); const queryResult = await container.executeCliCmd("info", ["clients"]); @@ -118,23 +118,8 @@ describe("RedisContainer", { timeout: 240_000 }, () => { // } }); - it("should start with redis-stack-server and json module", async () => { - // startWithRedisStack { - await using container = await new RedisContainer(REDISSTACK_IMAGE).withPassword("testPassword").start(); - - const client = createClient({ url: container.getConnectionUrl() }); - await client.connect(); - - await client.json.set("key", "$", { name: "test" }); - const result = await client.json.get("key"); - expect(result).toEqual({ name: "test" }); - - client.destroy(); - // } - }); - - it("should start redis with custom command", async () => { - const container = new RedisContainer(IMAGE).withCommand(["redis-server", "--loglevel", "verbose"]); + it.concurrent("should start redis with custom command", async () => { + const container = new RedisContainer(image).withCommand(["redis-server", "--loglevel", "verbose"]); await using startedContainer = await container.start(); // @ts-expect-error - accessing private property for testing @@ -149,12 +134,22 @@ describe("RedisContainer", { timeout: 240_000 }, () => { client.destroy(); }); - it("should start redis-stack with custom env", async () => { - const container = new RedisContainer(REDISSTACK_IMAGE).withEnvironment({ REDIS_ARGS: "--loglevel verbose" }); + it.concurrent("should start redis with custom command and keeping default args", async () => { + const sourcePath = fs.mkdtempSync("redis-"); + + const container = new RedisContainer(image) + .withCommand(["redis-server", "--loglevel", "verbose"]) + .withPersistence(sourcePath); await using startedContainer = await container.start(); // @ts-expect-error - accessing private property for testing - expect(container.createOpts.Env).toEqual(["REDIS_ARGS=--loglevel verbose"]); + expect(container.createOpts.Cmd).toEqual([ + "redis-server", + "--loglevel", + "verbose", + "--save 1 1 ", + "--appendonly yes", + ]); const client = createClient({ url: startedContainer.getConnectionUrl() }); await client.connect(); @@ -163,24 +158,32 @@ describe("RedisContainer", { timeout: 240_000 }, () => { expect(await client.get("key")).toBe("val"); client.destroy(); + fs.rmSync(sourcePath, { force: true, recursive: true }); }); +}); - it("should start redis with custom command and keeping default args", async () => { - const sourcePath = fs.mkdtempSync("redis-"); +describe(`RedisContainer (${REDISSTACK_IMAGE})`, { timeout: 240_000 }, () => { + it("should start with redis-stack-server and json module", async () => { + // startWithRedisStack { + await using container = await new RedisContainer(REDISSTACK_IMAGE).withPassword("testPassword").start(); - const container = new RedisContainer(IMAGE) - .withCommand(["redis-server", "--loglevel", "verbose"]) - .withPersistence(sourcePath); + const client = createClient({ url: container.getConnectionUrl() }); + await client.connect(); + + await client.json.set("key", "$", { name: "test" }); + const result = await client.json.get("key"); + expect(result).toEqual({ name: "test" }); + + client.destroy(); + // } + }); + + it("should start redis-stack with custom env", async () => { + const container = new RedisContainer(REDISSTACK_IMAGE).withEnvironment({ REDIS_ARGS: "--loglevel verbose" }); await using startedContainer = await container.start(); // @ts-expect-error - accessing private property for testing - expect(container.createOpts.Cmd).toEqual([ - "redis-server", - "--loglevel", - "verbose", - "--save 1 1 ", - "--appendonly yes", - ]); + expect(container.createOpts.Env).toEqual(["REDIS_ARGS=--loglevel verbose"]); const client = createClient({ url: startedContainer.getConnectionUrl() }); await client.connect(); @@ -189,7 +192,6 @@ describe("RedisContainer", { timeout: 240_000 }, () => { expect(await client.get("key")).toBe("val"); client.destroy(); - fs.rmSync(sourcePath, { force: true, recursive: true }); }); it("should start redis-stack with custom env and keeping default args", async () => { diff --git a/packages/modules/valkey/src/valkey-container.test.ts b/packages/modules/valkey/src/valkey-container.test.ts index ff82f5fa2..cb303533b 100644 --- a/packages/modules/valkey/src/valkey-container.test.ts +++ b/packages/modules/valkey/src/valkey-container.test.ts @@ -4,12 +4,12 @@ import { createClient } from "redis"; import { getImage } from "../../../testcontainers/src/utils/test-helper"; import { ValkeyContainer } from "./valkey-container"; -const IMAGE = getImage(__dirname); +const IMAGES = ["valkey/valkey:7.2.14", "valkey/valkey:8.1.10", getImage(__dirname)]; -describe("ValkeyContainer", { timeout: 240_000 }, () => { - it("should connect and execute set-get", async () => { +describe.each(IMAGES)("ValkeyContainer (%s)", { concurrent: false, timeout: 240_000 }, (image) => { + it.concurrent("should connect and execute set-get", async () => { // valkeyStartContainer { - await using container = await new ValkeyContainer(IMAGE).start(); + await using container = await new ValkeyContainer(image).start(); const client = createClient({ url: container.getConnectionUrl() }); await client.connect(); @@ -21,8 +21,8 @@ describe("ValkeyContainer", { timeout: 240_000 }, () => { // } }); - it("should connect with password and execute set-get", async () => { - await using container = await new ValkeyContainer(IMAGE).withPassword("test").start(); + it.concurrent("should connect with password and execute set-get", async () => { + await using container = await new ValkeyContainer(image).withPassword("test").start(); const client = createClient({ url: container.getConnectionUrl() }); await client.connect(); @@ -33,11 +33,11 @@ describe("ValkeyContainer", { timeout: 240_000 }, () => { client.destroy(); }); - it("should reconnect with volume and persistence data", async () => { + it.concurrent("should reconnect with volume and persistence data", async () => { // valkeyWithPersistentData { const sourcePath = fs.mkdtempSync("valkey-"); - await using container = await new ValkeyContainer(IMAGE).withPassword("test").withPersistence(sourcePath).start(); + await using container = await new ValkeyContainer(image).withPassword("test").withPersistence(sourcePath).start(); let client = createClient({ url: container.getConnectionUrl() }); await client.connect(); @@ -56,9 +56,9 @@ describe("ValkeyContainer", { timeout: 240_000 }, () => { // } }); - it("should load initial data and can read it", async () => { + it.concurrent("should load initial data and can read it", async () => { // valkeyWithPredefinedData { - await using container = await new ValkeyContainer(IMAGE) + await using container = await new ValkeyContainer(image) .withPassword("test") .withInitialData(path.join(__dirname, "initData.valkey")) .start(); @@ -77,12 +77,12 @@ describe("ValkeyContainer", { timeout: 240_000 }, () => { // } }); - it("should start with username and password", async () => { + it.concurrent("should start with username and password", async () => { // valkeyWithUsernameAndPassword { const username = "testUser"; const password = "testPassword"; - await using container = await new ValkeyContainer(IMAGE).withUsername(username).withPassword(password).start(); + await using container = await new ValkeyContainer(image).withUsername(username).withPassword(password).start(); expect(container.getConnectionUrl()).toEqual( `redis://${username}:${password}@${container.getHost()}:${container.getPort()}` @@ -98,11 +98,11 @@ describe("ValkeyContainer", { timeout: 240_000 }, () => { client.destroy(); }); - it("should start with password only", async () => { + it.concurrent("should start with password only", async () => { // valkeyWithPassword { const password = "testPassword"; - await using container = await new ValkeyContainer(IMAGE).withPassword(password).start(); + await using container = await new ValkeyContainer(image).withPassword(password).start(); expect(container.getConnectionUrl()).toEqual(`redis://:${password}@${container.getHost()}:${container.getPort()}`); // } @@ -116,9 +116,9 @@ describe("ValkeyContainer", { timeout: 240_000 }, () => { client.destroy(); }); - it("should execute container cmd and return the result", async () => { + it.concurrent("should execute container cmd and return the result", async () => { // valkeyExecuteCommand { - await using container = await new ValkeyContainer(IMAGE).start(); + await using container = await new ValkeyContainer(image).start(); const queryResult = await container.executeCliCmd("info", ["clients"]);