aclowkay
aclowkay

Reputation: 3877

Passing long configuration file to Kubernetes

I like the work methology of Kuberenetes, use self-contained image and pass the configuration in a ConfigMap, as a volume.

Now this worked great until I tried to do this thing with Liquibase container, The SQL is very long ~1.5K lines, and Kubernetes rejects it as too long.

Error from Kubernetes:

The ConfigMap "liquibase-test-content" is invalid: metadata.annotations: Too long: must have at most 262144 characters

I thought of passing the .sql files as a hostPath, but as I understand these hostPath's content is probably not going to be there

Is there any other way to pass configuration from the K8s directory to pods? Thanks.

Upvotes: 24

Views: 30090

Answers (4)

zehio
zehio

Reputation: 1

Just use a secret and b64enc.

They don't have the last-applied-configuration annotation.

Upvotes: 0

Chris
Chris

Reputation: 5643

Since 1.18 you can use server-side apply to circumvent the problem.

kubectl apply --server-side=true -f foo.yml

where server-side=true runs the apply command on the server instead of the client.

This will properly show conflicts with other actors, including client-side apply and thus fail:

Apply failed with 4 conflicts: conflicts with "kubectl-client-side-apply" using apiextensions.k8s.io/v1:
- .status.conditions
- .status.storedVersions
- .status.acceptedNames.kind
- .status.acceptedNames.plural
Please review the fields above--they currently have other managers. Here
are the ways you can resolve this warning:
* If you intend to manage all of these fields, please re-run the apply
  command with the `--force-conflicts` flag.
* If you do not intend to manage all of the fields, please edit your
  manifest to remove references to the fields that should keep their
  current managers.
* You may co-own fields by updating your manifest to match the existing
  value; in this case, you'll become the manager if the other manager(s)
  stop managing the field (remove it from their configuration).
See http://k8s.io/docs/reference/using-api/api-concepts/#conflicts

If the changes are intended you can simple use the first option:

kubectl apply --server-side=true --force-conflicts -f foo.yml

Upvotes: 23

David
David

Reputation: 1458

The error you are seeing is not about the size of the actual ConfigMap contents, but about the size of the last-applied-configuration annotation that kubectl apply automatically creates on each apply. If you use kubectl create -f foo.yaml instead of kubectl apply -f foo.yaml, it should work.

Please note that in doing this you will lose the ability to use kubectl diff and do incremental updates (without replacing the whole object) with kubectl apply.

Upvotes: 29

Michael Hausenblas
Michael Hausenblas

Reputation: 13941

You can use an init container for this. Essentially, put the .sql files on GitHub or S3 or really any location you can read from and populate a directory with it. The semantics of the init container guarantee that the Liquibase container will only be launched after the config files have been downloaded.

Upvotes: 6

Related Questions