Djabx
Djabx

Reputation: 745

How can I create a namespace with kustomize?

I've a simple project that use kustomize like this:

base/
  namespace.yaml
  kustomization.yaml
  service.yaml

With kustomization.yaml is:

resources:
  - namespace.yaml
  - service.yaml
namespace: my_wanted_namespace

And namespace.yaml is:

apiVersion: v1
kind: Namespace
metadata:
  name: default

The problem is that when I do: kustomize build ./base

I've this:

apiVersion: v1
kind: Namespace
metadata:
  name: default

How can I have

apiVersion: v1
kind: Namespace
metadata:
  name: my_wanted_namespace

Thanks.

Upvotes: 32

Views: 46531

Answers (6)

rfreytag
rfreytag

Reputation: 1330

From my experience, the simplest answer is this:

in base

  • do NOT include a namespace.yaml
  • do NOT add namespace to your resources

in overlay or environment

  • add a namespace.yaml if you need to create a dedicated namespace
  • add the namespace: my-name to the kustomization.yaml in your overlay

folder structure

so the structure is like this

base/
 - service.yaml
 - ...
 - kustomization.yaml
overlays/
 - some-overlay/
   - namespace.yaml # (optional) can be defined here
   - kustomization.yaml
environments/
 - environment-1/
   - namespace.yaml # or define it here
   - kustomization.yaml # with namespace: my-name

you can see in kustomize build . output of the environment that all resources are correctly scoped to the namespace.

for reference:

# kustomization.yaml in environment
apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization

namespace: my-namespace

bases:
- ../base/

resources:
- namespace.yaml

See documentation here: https://kubectl.docs.kubernetes.io/references/kustomize/kustomization/namespace/

Upvotes: 5

iDen
iDen

Reputation: 75

Old post but I have another example to include for future wanderers.

In your base, you can have Namespace declared using namespace.yaml. I.e. that will be a default value.

base/
  namespace.yaml
  kustomization.yaml
  ...

Example base/namespace.yaml contents:

apiVersion: v1
kind: Namespace
metadata:
  name: default

In your overlay/kustomization.yaml use PatchTransformer to update value of the default namespace without creating namespace resource in each overlay directory.

Example overlay/kustomization.yaml contents:

namespace: my-wanted-namespace

resources:
- ../base

patches:
- target:
    kind: Namespace
    name: default
  patch: |-
    - op: replace
      path: /metadata/name
      value: my-wanted-namespace

Upvotes: 4

Brian C
Brian C

Reputation: 101

Old post, but the above answers are more complicated than needed.

In kustomization.yaml

apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization

namespace: my-desired-namespace
resources:
- namespace.yaml

and in namespace.yaml

apiVersion: v1
kind: Namespace
metadata:
  name: intentionally.broken.namespace

Realistically, I have a folder elsewhere with a kustomization and the dummy namespace that I can include as a resource from any of my kustomizations. The kustomization will replace the Namespace name with the namespace transformer, and create it.

Upvotes: 10

Martín Coll
Martín Coll

Reputation: 3794

You can remove the namespace resource from base and only include it in the overlay. E.g:

overlay/kustomization.yaml

namespace: my_wanted_namespace
bases:
- ../base
resources:
- namespace.yaml

overlay/namespace.yaml

apiVersion: v1
kind: Namespace
metadata:
  name: my_wanted_namespace

It is important that the namespace property in the kustomization.yaml file matches the name in the namespace.yaml resource and that base/service.yaml doesn't set the namespace property.


EDIT: original response below

As an alternative to Hadrien's answer, JSON Patch also worked for me:

namespace: my-wanted-namespace
patchesJSON6902:
- target:
    version: v1
    kind: Namespace
    name: base-namespace
  patch: |-
    - op: replace
      path: /metadata/name
      value: my-wanted-namespace

The key of this method is transforming the base Namespace name to match exactly the namespace key in the overlay kustomization.yaml file.

Upvotes: 14

Hadrien TOMA
Hadrien TOMA

Reputation: 2723

In order to be able to create a namespace on the fly and use it for the other resources Kustomize will customize, you can use this trick:


namespace=${1:-"my-namespace-meaning"}

rm -rf ./base
mkdir ./base

cat <<EOF > ./base/namespace.yaml
apiVersion: v1
kind: Namespace
metadata:
  name: suffix
EOF

cat <<EOF > ./base/service.yaml
apiVersion: v1
kind: Service
metadata:
  name: docker-registry
  labels:
    name: docker-registry
spec:
  ports:
    - port: 5001
      targetPort: 5000
  selector:
    name: docker-registry
  type: ClusterIP
EOF

cat <<EOF > ./base/deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
  name: docker-registry
spec:
  replicas: 1
  selector:
    matchLabels:
      app: docker-registry
  template:
    metadata:
      labels:
        app: docker-registry
    spec:
      containers:
        - name: docker-registry
          image: registry
          ports:
            - containerPort: 5000
          resources:
            limits:
              memory: 200Mi
              cpu: 300m
            requests:
              memory: 100Mi
              cpu: 100m
EOF

cat <<EOF > ./kustomization.yaml
namePrefix: "${namespace}-"

namespace: "${namespace}-suffix"

resources:
- base/deployment.yaml
- base/namespace.yaml
- base/service.yaml
EOF

kubectl kustomize ./

Running this script will output:

apiVersion: v1
kind: Namespace
metadata:
  name: my-namespace-meaning-suffix
---
apiVersion: v1
kind: Service
metadata:
  labels:
    name: docker-registry
  name: my-namespace-meaning-docker-registry
  namespace: my-namespace-meaning-suffix
spec:
  ports:
  - port: 5001
    targetPort: 5000
  selector:
    name: docker-registry
  type: ClusterIP
---
apiVersion: apps/v1
kind: Deployment
metadata:
  name: my-namespace-meaning-docker-registry
  namespace: my-namespace-meaning-suffix
spec:
  replicas: 1
  selector:
    matchLabels:
      app: docker-registry
  template:
    metadata:
      labels:
        app: docker-registry
    spec:
      containers:
      - image: registry
        name: docker-registry
        ports:
        - containerPort: 5000
        resources:
          limits:
            cpu: 300m
            memory: 200Mi
          requests:
            cpu: 100m
            memory: 100Mi

The idea is to first use the namePrefix keyword (doc here) in order to deterministically define the value of the namespace after customization. Then this customized namespace can be used for each other resource thanks to the namespace keyword (doc here).

Upvotes: 2

azak
azak

Reputation: 549

If you want to create your namespace with kustomize, your kustomize file should look like this. It has to use the namespace.

apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization
namespace: my-wanted-namespace
resources:
- ./namespace.yml

And your namespace file should be a normal namespace deployment like this:

apiVersion: v1
kind: Namespace
metadata:
  name: my-wanted-namespace

Upvotes: 29

Related Questions