Reputation: 272
I'm trying to create a Redis container in Docker and run a command to initialize the data structures. But I can't even get a simple command like redis-cli SET counter "4"
to work.
But even with a command like redis-cli --help
, it doesn't work. It seems that after any command, it exists with the line:
sockets_server_redis_1 exited with code 1
When I use either of the following lines:
command: "redis-cli SET counter \"4\" && redis-cli GET counter"
command: sh -c "redis-cli SET counter \"4\" && redis-cli GET counter"
the complete output I get is:
Attaching to sockets_server_redis_1
redis_1 | Could not connect to Redis at 127.0.0.1:6379: Connection refused
sockets_server_redis_1 exited with code 1
This is my docker-compose.yml file:
version: "3.8"
services:
redis:
image: redis
command: "redis-cli SET counter \"4\" && redis-cli GET counter"
ports:
- 6379:6379
However, if I run this command in the CLI through Docker, it works.
So, I have two questions:
Why do the set and get commands not work but redis-cli --help
works?
Why does the process exit after the initial command, and how can I initialize the data structures and not have it exit?
Upvotes: 2
Views: 1299
Reputation: 7522
The command
instruction in a Docker Compose file maps to the CMD directive in a Dockerfile, which is the one and only command that the container will execute upon launching (the command can always be overridden when you launch the container, which is what docker-compose is doing under the hood when you set that option).
For a Redis container, whose purpose is to bring up a Redis server, the command should always be the command that actually launches the server. When you override it to instead run redis-cli commands, the server does not come up, so the client can't connect and you see the errors you're getting. The --help
option for redis-cli doesn't open a connection, which is why it doesn't error (to answer your question #1).
For question #2, see above as to why the process is exiting after the command
runs. To actually solve your problem, there are a range of options, but I would suggest a second container which just runs a script that a) waits until Redis is reachable and b) initializes the data structures once it is. A utility like wait-for-it can make step A easier, though you might be able to get away with just Compose's default depends_on
functionality (it doesn't wait for the actual service to be ready, just the container, but Redis comes up very quickly):
version: "3.8"
services:
redis:
image: redis
ports:
- 6379:6379
redis_init:
image: redis # we need an image with redis-cli available, so might as well re-use it
command: "redis-cli -h redis SET counter \"4\""
depends_on:
- redis
From testing locally, this works, though I can't say how reliable it might be on every system.
Upvotes: 2