1

I can't find a proper way to implements what I want. I have a StatefulSet, running several identical several pods of code which use a database. I need the database to be pre-populated first (tables, schemas, etc). So I use init-containers and everything is going well: the StatefulSet launchs one pod at a time sequentially, the init-container is fired, does its job, then the same thing happens for each other container, the init container ends very quickly as their is nothing more to do.

---
kind: StatefulSet
apiVersion: apps/v1
metadata:
  name: the-name-1
spec:
  replicas: 3
  selector:
    matchLabels:
      name: the-name-1
  template:
    metadata:
      labels:
        name: the-name-1
    spec:
      initContainers:
        - name: init
          image: registry/image1
          command: ["/bin/sh"]
          args: ["-c", "set -e; /scripts/pre-populate-db.sh;"]
      containers:
        - name: container-1
          image: registry/image1

But, now I also have a second StatefulSet, which also requires the database to be pre-populated. So this second StatefulSet needs for a least one container of the first StatefulSet to have be launched successfully.

I can't find a proper way to tell this StatefulSet: wait for the first StatefulSet to have done its job. I precise, proper, as I don't want to have an init-container which says sleep n seconds.

As the code in question is legacy, I can't go on a solution which involves code modifications, such as a script in an init container which goes in the database to check if something is set correctly, I want a pure Kubernetes solution.

  • Is there a way to tell StatefulSet pods to wait for a "Kubernetes something" to be ready before being launched?
  • Is there a way to run a Kubernetes Job and made Deployment/StatefulSet dependent on that Job being executed correctly?
dbourcet
  • 175
  • 1
  • 2
  • 10
  • is your first statefulset is listen in one specific tcp port? – c4f4t0r Jun 17 '19 at 09:29
  • Yes the first StatefulSet pods are listening on a specific port. – dbourcet Jun 17 '19 at 09:48
  • you need to create a headless service with your first statefulset and in the second one you need to create a initcontainer that try to do telnet firstapp-0.namespace.svc.cluster.local port number, so the second statefulset will be running only when the first one will answer to the tcp request – c4f4t0r Jun 17 '19 at 10:25

1 Answers1

2

I tested using the following statefulset example: https://raw.githubusercontent.com/kubernetes/website/master/content/en/examples/application/web/web.yaml

Now in the second statefulset I used an initcontainer with this bash code:

while true;do sleep 2; curl http://web-0.nginx/ && break ;done

In this way, the second statefulset will be run only when first copy of the first one will be available.

c4f4t0r
  • 5,149
  • 3
  • 28
  • 41
  • Thanks for the workaround, as it works as expected. But do you know some way that only use Kubernetes native resource, such as "when this Job has ended", "when this StatefulSet status is up". Does this kind of ordonnancing exists in Kubernetes? because I can't find any. – dbourcet Jun 17 '19 at 14:05
  • @koudougou if it works mark the answer as solution, in any case from what I know, there is not dependencies as you want in kubernetes – c4f4t0r Jun 17 '19 at 17:46