I have kubernetes job defined as following:
apiVersion: batch/v1
kind: Job
metadata:
name: redis-master
namespace: sandbox
labels:
app: redis
spec:
parallelism: 1
ttlSecondsAfterFinished: 10
template:
metadata:
labels:
app: redis
spec:
containers:
- name: master
image: redis
command: ["sh", "-c"]
args:
- redis-server
- sleep 10
- redis-cli RPUSH codes $(cat /data/codes)
env:
- name: MASTER
value: "true"
ports:
- containerPort: 6379
volumeMounts:
- name: codes
mountPath: /data/codes
subPath: codes
readOnly: true
volumes:
- name: codes
configMap:
name: codes
restartPolicy: Never
when pod is up and running redis is empty:
/deploy/base$ kubectl exec -it -n box redis-master-mbhrk -- /bin/sh
# redis-cli lrange codes 0 -1
(empty array)
#
this pod should kill him self when the queue codes is empty.
also, i get an error in pod console
can't access tty; job control turned off
how can I load a codes to redis ???
CodePudding user response:
A container only runs one command. You've set that command to /bin/sh -c
and passed it a command string to run (redis-server
), along with two additional parameters which would be visible inside that command string as $0
and $1
.
The first thing you need to do is split the Redis server proper into a separate container, probably managed by a StatefulSet (or perhaps a Deployment if persistence is disabled). You might use something like a prepackaged Helm chart to simplify deploying this. We'll assume this already exists:
apiVersion: v1
kind: Service
metadata:
name: redis-server
...
Now your Job needs to only run the redis-cli RPUSH
command. Because of the way you use a command substitution, you do need a shell here. However, since you're not running the Redis server here, you don't need various bits of machinery around that.
You could probably write the Job as:
apiVersion: batch/v1
kind: Job
metadata:
name: load-codes
namespace: sandbox
# labels:
# app: redis
spec:
template:
# metadata:
# labels:
# app: redis
spec:
containers:
- name: loader
image: redis
command:
- /bin/sh
- -c
- redis-cli -h redis-server RPUSH codes $(cat /data/codes)
volumeMounts:
- name: codes
mountPath: /data
readOnly: true
volumes:
- name: codes
configMap:
name: codes
restartPolicy: OnFailure
You'll probably need to set the labels so that they're not picked up by the main Service (since the pod isn't running a Redis server). I've also set the restart policy to OnFailure
: if the pod does fail for some reason, maybe because the Redis server isn't available yet, this will automatically restart it, but if it succeeds, the Job will be marked "completed".
CodePudding user response:
The issue was in
args:
- redis-server
- sleep 10
Command redis-server is command which brings redis server up. So next command can not be executed because redis-server is still running.