nyl 0.6.0__tar.gz → 0.7.0__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- nyl-0.7.0/.changelog/0.7.0.toml +70 -0
- {nyl-0.6.0 → nyl-0.7.0}/.github/workflows/docker.yaml +4 -4
- {nyl-0.6.0 → nyl-0.7.0}/.github/workflows/python.yaml +33 -5
- nyl-0.7.0/.github/workflows/update-flake-lock.yaml +23 -0
- {nyl-0.6.0 → nyl-0.7.0}/PKG-INFO +10 -3
- {nyl-0.6.0 → nyl-0.7.0}/README.md +8 -1
- {nyl-0.6.0 → nyl-0.7.0}/argocd-cmp/Dockerfile +3 -3
- {nyl-0.6.0 → nyl-0.7.0}/argocd-with-nyl/argocd.yaml +2 -2
- nyl-0.7.0/docs/content/changelog.md +69 -0
- {nyl-0.6.0 → nyl-0.7.0}/docs/content/reference/applysets.md +1 -1
- {nyl-0.6.0 → nyl-0.7.0}/docs/content/reference/argocd-plugin.md +1 -1
- {nyl-0.6.0 → nyl-0.7.0}/docs/content/reference/templating/inlining/helmcharts.md +3 -0
- {nyl-0.6.0 → nyl-0.7.0}/docs/content/reference/templating/inlining/postprocessor.md +38 -2
- {nyl-0.6.0 → nyl-0.7.0}/flake.nix +1 -1
- {nyl-0.6.0 → nyl-0.7.0}/pyproject.toml +20 -1
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/commands/__init__.py +1 -1
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/commands/new.py +20 -11
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/commands/run.py +5 -5
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/commands/template.py +96 -71
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/commands/tools/sops.py +1 -1
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/generator/helmchart.py +8 -4
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/profiles/__init__.py +2 -2
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/profiles/kubeconfig.py +3 -3
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/profiles/tunnel.py +2 -2
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/project/config.py +1 -1
- nyl-0.7.0/src/nyl/resources/helmchart_test.py +81 -0
- nyl-0.7.0/src/nyl/resources/postprocessor.py +206 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/resources/postprocessor_test.py +18 -2
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/secrets/sops.py +4 -4
- nyl-0.7.0/src/nyl/tools/kubernetes.py +69 -0
- nyl-0.6.0/src/nyl/resources/postprocessor.py +0 -128
- nyl-0.6.0/src/nyl/tools/kubernetes.py +0 -34
- {nyl-0.6.0 → nyl-0.7.0}/.envrc +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/.github/workflows/docs.yaml +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/.gitignore +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/argocd-cmp/README.md +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/argocd-cmp/plugin.yaml +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/argocd-with-nyl/.envrc +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/argocd-with-nyl/.secrets.yaml +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/argocd-with-nyl/.sops.yaml +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/argocd-with-nyl/README.md +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/argocd-with-nyl/nyl-project.yaml +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/argocd-with-nyl/nyl-secrets.yaml +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/docs/content/index.md +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/docs/content/reference/cluster-connectivity.md +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/docs/content/reference/configuration/environment.md +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/docs/content/reference/configuration/profiles.md +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/docs/content/reference/configuration/projects.md +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/docs/content/reference/configuration/secrets.md +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/docs/content/reference/configuration-api/profiles.md +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/docs/content/reference/configuration-api/secrets.md +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/docs/content/reference/glossary.md +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/docs/content/reference/templating/basics.md +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/docs/content/reference/templating/components.md +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/docs/content/reference/templating/inlining/overview.md +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/docs/content/reference/templating/secrets.md +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/docs/mkdocs.yml +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/docs/pyproject.toml +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/docs/uv.lock +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/example/manifests/postgres.yaml +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/example/nyl-profiles.yaml +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/example/nyl-secrets.yaml +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/example/secrets.yaml +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/flake.lock +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/nix/uv.nix +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/renovate.json +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/kubernetes/README.md +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/kubernetes/__init__.pyi +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/kubernetes/dynamic/__init__.pyi +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/kubernetes/dynamic/client.pyi +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/kubernetes/dynamic/discovery.pyi +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/kubernetes/dynamic/exceptions.pyi +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/kubernetes/dynamic/resource.pyi +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/kubernetes/watch/__init__.pyi +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/kubernetes/watch/watch.pyi +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/__init__.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/commands/argocd.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/commands/crds.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/commands/profile.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/commands/secrets.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/commands/tools/__init__.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/commands/tools/bcrypt.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/commands/tun.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/generator/__init__.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/generator/components.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/generator/dispatch.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/generator/dispatch_test.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/generator/statefulsecret.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/profiles/config.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/profiles/config_test.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/resources/__init__.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/resources/applyset.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/resources/applyset_test.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/resources/helmchart.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/resources/placeholder.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/resources/statefulsecret.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/secrets/__init__.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/secrets/config.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/secrets/config_test.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/secrets/kubernetes.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/secrets/null.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/secrets/sops_test.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/templating.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/templating_test.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/tools/di.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/tools/fs.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/tools/fs_test.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/tools/kubectl.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/tools/kvstore.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/tools/loads.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/tools/logging.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/tools/shell.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/tools/testing.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/tools/typer.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/tools/types.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/src/nyl/tools/yaml.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/tests/__init__.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/tests/conftest.py +0 -0
- {nyl-0.6.0 → nyl-0.7.0}/uv.lock +0 -0
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
release-date = "2025-01-17"
|
|
2
|
+
|
|
3
|
+
[[entries]]
|
|
4
|
+
id = "d86d5d47-3d02-4321-94a3-bea25c512ecc"
|
|
5
|
+
type = "breaking change"
|
|
6
|
+
description = "Recognize `nyl.io/default-namespace: \"true\"` on Namespace resources to choose between one of multiple namespaces defined in the same manifest file."
|
|
7
|
+
author = "@NiklasRosenstein"
|
|
8
|
+
|
|
9
|
+
[[entries]]
|
|
10
|
+
id = "056ab3d5-fc80-449c-af24-d7bca6f3e522"
|
|
11
|
+
type = "breaking change"
|
|
12
|
+
description = "Instead of not assuming a default namespace when multiple `Namespace` resources are defined in a manifest file, pick the first one alphabetically when none have the `nyl.io/default-namespace: \"true\"` annotation"
|
|
13
|
+
author = "@NiklasRosenstein"
|
|
14
|
+
|
|
15
|
+
[[entries]]
|
|
16
|
+
id = "d0798272-7c1c-402d-8e04-d578cea6a410"
|
|
17
|
+
type = "improvement"
|
|
18
|
+
description = "Apply Nyl `PostProcessor` instructions at the end, after Nyl had a chance to fill in the manifest file's determined default namespace. Kyverno might add the `namespace: default` field to any resource that has no namespace set, making it impossbile for Nyl after the fact to tell which resources need to have their namespace injected."
|
|
19
|
+
author = "@NiklasRosenstein"
|
|
20
|
+
|
|
21
|
+
[[entries]]
|
|
22
|
+
id = "8a3b94a4-0dd9-45a0-8cb2-bd679979527e"
|
|
23
|
+
type = "fix"
|
|
24
|
+
description = "Update `PostProcessor`, pointing Kyverno to a directory and expecting it to output all manifest, not just the mutated ones. The `PostProcessor` is now invoked at the very end, even after Nyl patches resources with the default namespace in the current manifest file."
|
|
25
|
+
author = "@NiklasRosenstein"
|
|
26
|
+
|
|
27
|
+
[[entries]]
|
|
28
|
+
id = "843a3744-7e50-49d3-8dc5-8800e866ca01"
|
|
29
|
+
type = "fix"
|
|
30
|
+
description = "fix #57 -- `ARGOCD_APP_NAMESPACE` and the `--default-namespace` option are used now only when no namespace is defined in the manifest file"
|
|
31
|
+
author = "@NiklasRosenstein"
|
|
32
|
+
|
|
33
|
+
[[entries]]
|
|
34
|
+
id = "3152517a-b701-4d38-ba18-f97f2f03cd09"
|
|
35
|
+
type = "improvement"
|
|
36
|
+
description = "Resources generated by the Nyl `HelmChart` resource now get the chart resource's `metadata.namespace` populated before they are passed up and inlined into the rest of the manifest. Fixes #56"
|
|
37
|
+
author = "@NiklasRosenstein"
|
|
38
|
+
|
|
39
|
+
[[entries]]
|
|
40
|
+
id = "cdbd2567-9801-4514-8552-6fdc352a8185"
|
|
41
|
+
type = "improvement"
|
|
42
|
+
description = "Fix deprecation warnings of using the `loguru.logger.opt(ansi)` keyword argument and use the new `colors` kwarg instead"
|
|
43
|
+
author = "@NiklasRosenstein"
|
|
44
|
+
|
|
45
|
+
[[entries]]
|
|
46
|
+
id = "dd1038ab-19cf-406a-bc06-ccc14ad8fbbb"
|
|
47
|
+
type = "feature"
|
|
48
|
+
description = "Add `PostProcessor.spec.kyvernoRules` field as a shorthand for defining Kyverno policies in a Nyl manifest."
|
|
49
|
+
author = "@NiklasRosenstein"
|
|
50
|
+
|
|
51
|
+
[[entries]]
|
|
52
|
+
id = "2eed140a-4d16-448a-96fb-997b3ca81297"
|
|
53
|
+
type = "refactor"
|
|
54
|
+
description = "Refactor `PostProcessor` implementation for generating policy files and invoking Kyverno"
|
|
55
|
+
author = "@NiklasRosenstein"
|
|
56
|
+
|
|
57
|
+
[[entries]]
|
|
58
|
+
id = "320c1dce-1ba6-451b-9f25-a279ae8b9eb2"
|
|
59
|
+
type = "improvement"
|
|
60
|
+
description = "`PostProcessor` log for invoking Kyverno now lists the policy file paths that are going to be applied"
|
|
61
|
+
author = "@NiklasRosenstein"
|
|
62
|
+
|
|
63
|
+
[[entries]]
|
|
64
|
+
id = "138bdc5d-848b-45fe-a5f4-4c658535339d"
|
|
65
|
+
type = "fix"
|
|
66
|
+
description = "`nyl new chart` now generates 2-space indented YAML and has a more complete template"
|
|
67
|
+
author = "@NiklasRosenstein"
|
|
68
|
+
issues = [
|
|
69
|
+
"https://github.com/NiklasRosenstein/nyl/issues/47",
|
|
70
|
+
]
|
|
@@ -36,8 +36,8 @@ jobs:
|
|
|
36
36
|
push: true
|
|
37
37
|
file: argocd-cmp/Dockerfile
|
|
38
38
|
tags: |
|
|
39
|
-
ghcr.io/
|
|
40
|
-
${{ github.ref_type == 'tag' && format('ghcr.io/
|
|
41
|
-
cache-to: type=registry,ref=ghcr.io/
|
|
42
|
-
cache-from: type=registry,ref=ghcr.io/
|
|
39
|
+
ghcr.io/helsing-ai/nyl/argocd-cmp:${{ github.sha }}
|
|
40
|
+
${{ github.ref_type == 'tag' && format('ghcr.io/helsing-ai/nyl/argocd-cmp:{0}', github.ref_name) || '' }}
|
|
41
|
+
cache-to: type=registry,ref=ghcr.io/helsing-ai/nyl/argocd-cmp:cache,mode=max
|
|
42
|
+
cache-from: type=registry,ref=ghcr.io/helsing-ai/nyl/argocd-cmp:cache
|
|
43
43
|
platforms: linux/amd64,linux/arm64
|
|
@@ -8,7 +8,7 @@ on:
|
|
|
8
8
|
branches: [ develop ]
|
|
9
9
|
|
|
10
10
|
jobs:
|
|
11
|
-
test:
|
|
11
|
+
test-nix:
|
|
12
12
|
runs-on: ubuntu-latest
|
|
13
13
|
|
|
14
14
|
steps:
|
|
@@ -22,12 +22,40 @@ jobs:
|
|
|
22
22
|
with:
|
|
23
23
|
name: mycache
|
|
24
24
|
|
|
25
|
-
|
|
26
|
-
- run: nix
|
|
25
|
+
# Ignore failures until we can fix the Nix build.
|
|
26
|
+
- run: nix flake check || true
|
|
27
|
+
- run: nix run .#test || true
|
|
28
|
+
|
|
29
|
+
test-native:
|
|
30
|
+
runs-on: ubuntu-latest
|
|
31
|
+
|
|
32
|
+
steps:
|
|
33
|
+
- uses: actions/checkout@v4
|
|
34
|
+
|
|
35
|
+
- uses: kyverno/action-install-cli@v0.2.0
|
|
36
|
+
with:
|
|
37
|
+
release: 'v1.13.2'
|
|
38
|
+
|
|
39
|
+
- name: Install SOPS
|
|
40
|
+
run: |
|
|
41
|
+
curl -LO https://github.com/getsops/sops/releases/download/v3.9.3/sops-v3.9.3.linux.amd64
|
|
42
|
+
mv sops-v3.9.3.linux.amd64 /usr/local/bin/sops
|
|
43
|
+
chmod +x /usr/local/bin/sops
|
|
44
|
+
|
|
45
|
+
- name: Install uv
|
|
46
|
+
uses: astral-sh/setup-uv@v5
|
|
47
|
+
with:
|
|
48
|
+
version: "0.5.20"
|
|
49
|
+
|
|
50
|
+
- run: uv sync
|
|
51
|
+
- run: uv run pytest .
|
|
52
|
+
- run: uv run mypy .
|
|
53
|
+
- run: uv run ruff check .
|
|
54
|
+
- run: uv run ruff format --check .
|
|
27
55
|
|
|
28
56
|
publish:
|
|
29
57
|
runs-on: ubuntu-latest
|
|
30
|
-
needs: test
|
|
58
|
+
needs: test-native
|
|
31
59
|
environment: release
|
|
32
60
|
permissions:
|
|
33
61
|
id-token: write
|
|
@@ -45,7 +73,7 @@ jobs:
|
|
|
45
73
|
python-version: "3.10"
|
|
46
74
|
|
|
47
75
|
- name: Bump version
|
|
48
|
-
run: sed 's/version = "
|
|
76
|
+
run: sed 's/version = ".*"/version = "${{ github.ref_name }}"/' -i pyproject.toml && git diff
|
|
49
77
|
|
|
50
78
|
- name: Install uv
|
|
51
79
|
run: python -m pip install uv
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
# See https://github.com/determinateSystems/update-flake-lock
|
|
2
|
+
|
|
3
|
+
name: update-flake-lock
|
|
4
|
+
on:
|
|
5
|
+
workflow_dispatch: # allows manual triggering
|
|
6
|
+
schedule:
|
|
7
|
+
- cron: '0 0 * * 0' # runs weekly on Sunday at 00:00
|
|
8
|
+
|
|
9
|
+
jobs:
|
|
10
|
+
lockfile:
|
|
11
|
+
runs-on: ubuntu-latest
|
|
12
|
+
steps:
|
|
13
|
+
- name: Checkout repository
|
|
14
|
+
uses: actions/checkout@v4
|
|
15
|
+
- name: Install Nix
|
|
16
|
+
uses: DeterminateSystems/nix-installer-action@main
|
|
17
|
+
- name: Update flake.lock
|
|
18
|
+
uses: DeterminateSystems/update-flake-lock@main
|
|
19
|
+
with:
|
|
20
|
+
pr-title: "Update flake.lock" # Title of PR to be created
|
|
21
|
+
pr-labels: | # Labels to be set on the PR
|
|
22
|
+
dependencies
|
|
23
|
+
automated
|
{nyl-0.6.0 → nyl-0.7.0}/PKG-INFO
RENAMED
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
Metadata-Version: 2.
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
2
|
Name: nyl
|
|
3
|
-
Version: 0.
|
|
3
|
+
Version: 0.7.0
|
|
4
4
|
Summary: Advanced templating engine for Kubernetes and GitOps.
|
|
5
5
|
Author-email: Niklas Rosenstein <rosensteinniklas@gmail.com>
|
|
6
6
|
License: MIT
|
|
@@ -34,7 +34,7 @@ Requires Python 3.11 or newer.
|
|
|
34
34
|
For some features, additional programs must be available:
|
|
35
35
|
|
|
36
36
|
* [kubectl](https://kubernetes.io/de/docs/reference/kubectl/) for most operations
|
|
37
|
-
* [kyverno](https://kyverno.io/docs/kyverno-cli/) when using the Nyl `PostProcessor` resource
|
|
37
|
+
* [kyverno](https://kyverno.io/docs/kyverno-cli/) ^1.13.x when using the Nyl `PostProcessor` resource
|
|
38
38
|
* [sops](https://github.com/getsops/sops) when using the SOPS secrets provider
|
|
39
39
|
|
|
40
40
|
You can install Nyl with Nix to ensure all dependencies are met.
|
|
@@ -53,6 +53,13 @@ And to format code, run
|
|
|
53
53
|
|
|
54
54
|
$ nix fmt
|
|
55
55
|
|
|
56
|
+
To build or serve the documentation, run
|
|
57
|
+
|
|
58
|
+
$ nix run .#docs serve
|
|
59
|
+
$ nix run .#docs build
|
|
60
|
+
|
|
61
|
+
respectively.
|
|
62
|
+
|
|
56
63
|
## Tracking upstream information
|
|
57
64
|
|
|
58
65
|
* Discussion around ArgoCD supporting Helm lookups (maybe with Project-level service account?), see
|
|
@@ -12,7 +12,7 @@ Requires Python 3.11 or newer.
|
|
|
12
12
|
For some features, additional programs must be available:
|
|
13
13
|
|
|
14
14
|
* [kubectl](https://kubernetes.io/de/docs/reference/kubectl/) for most operations
|
|
15
|
-
* [kyverno](https://kyverno.io/docs/kyverno-cli/) when using the Nyl `PostProcessor` resource
|
|
15
|
+
* [kyverno](https://kyverno.io/docs/kyverno-cli/) ^1.13.x when using the Nyl `PostProcessor` resource
|
|
16
16
|
* [sops](https://github.com/getsops/sops) when using the SOPS secrets provider
|
|
17
17
|
|
|
18
18
|
You can install Nyl with Nix to ensure all dependencies are met.
|
|
@@ -31,6 +31,13 @@ And to format code, run
|
|
|
31
31
|
|
|
32
32
|
$ nix fmt
|
|
33
33
|
|
|
34
|
+
To build or serve the documentation, run
|
|
35
|
+
|
|
36
|
+
$ nix run .#docs serve
|
|
37
|
+
$ nix run .#docs build
|
|
38
|
+
|
|
39
|
+
respectively.
|
|
40
|
+
|
|
34
41
|
## Tracking upstream information
|
|
35
42
|
|
|
36
43
|
* Discussion around ArgoCD supporting Helm lookups (maybe with Project-level service account?), see
|
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
#: -----------------
|
|
4
4
|
|
|
5
5
|
FROM python:3.13-alpine AS build
|
|
6
|
-
COPY --from=ghcr.io/astral-sh/uv:0.5.
|
|
6
|
+
COPY --from=ghcr.io/astral-sh/uv:0.5.7 /uv /bin/uv
|
|
7
7
|
|
|
8
8
|
WORKDIR /opt/nyl
|
|
9
9
|
|
|
@@ -59,7 +59,7 @@ RUN curl -fsSL -o get_helm.sh https://raw.githubusercontent.com/helm/helm/main/s
|
|
|
59
59
|
FROM fetch-bin-base AS sops-bin
|
|
60
60
|
# Find SOPS releases at https://github.com/getsops/sops/releases
|
|
61
61
|
# renovate: datasource=github-releases depName=sops packageName=getsops/sops
|
|
62
|
-
ARG SOPS_VERSION=v3.9.
|
|
62
|
+
ARG SOPS_VERSION=v3.9.2
|
|
63
63
|
RUN curl -fLO https://github.com/getsops/sops/releases/download/${SOPS_VERSION}/sops-${SOPS_VERSION}.linux.$(cat /BINARY_ARCH) \
|
|
64
64
|
&& mv sops-${SOPS_VERSION}.linux.$(cat /BINARY_ARCH) /usr/local/bin/sops \
|
|
65
65
|
&& chmod +x /usr/local/bin/sops \
|
|
@@ -68,7 +68,7 @@ RUN curl -fLO https://github.com/getsops/sops/releases/download/${SOPS_VERSION}/
|
|
|
68
68
|
|
|
69
69
|
FROM fetch-bin-base AS kyverno-bin
|
|
70
70
|
# renovate: datasource=github-releases depName=kyverno packageName=kyverno/kyverno
|
|
71
|
-
ARG KYVERNO_VERSION=1.13.
|
|
71
|
+
ARG KYVERNO_VERSION=1.13.2
|
|
72
72
|
RUN \
|
|
73
73
|
case "$(uname -m)" in \
|
|
74
74
|
x86_64) KYVERNO_ARCH='x86_64' ;; \
|
|
@@ -40,7 +40,7 @@ spec:
|
|
|
40
40
|
repoServer:
|
|
41
41
|
extraContainers:
|
|
42
42
|
- name: nyl-v1
|
|
43
|
-
image: ghcr.io/
|
|
43
|
+
image: ghcr.io/helsing-ai/nyl/argocd-cmp:0.0.7
|
|
44
44
|
securityContext:
|
|
45
45
|
runAsNonRoot: true
|
|
46
46
|
runAsUser: 999
|
|
@@ -76,7 +76,7 @@ metadata:
|
|
|
76
76
|
spec:
|
|
77
77
|
project: default
|
|
78
78
|
source:
|
|
79
|
-
repoURL: https://github.com/
|
|
79
|
+
repoURL: https://github.com/helsing-ai/nyl.git
|
|
80
80
|
targetRevision: HEAD
|
|
81
81
|
path: argocd-with-nyl
|
|
82
82
|
destination:
|
|
@@ -0,0 +1,69 @@
|
|
|
1
|
+
# Changelog
|
|
2
|
+
|
|
3
|
+
## 0.7.0
|
|
4
|
+
|
|
5
|
+
<table><tr><th>Type</th><th>Description</th><th>PR</th><th>Issues</th><th>Author</th></tr>
|
|
6
|
+
<tr><td>Breaking change</td><td>
|
|
7
|
+
|
|
8
|
+
Recognize `nyl.io/default-namespace: "true"` on Namespace resources to choose between one of multiple namespaces defined in the same manifest file.</td><td></td><td></td><td>@NiklasRosenstein</td></tr>
|
|
9
|
+
<tr><td>Breaking change</td><td>
|
|
10
|
+
|
|
11
|
+
Instead of not assuming a default namespace when multiple `Namespace` resources are defined in a manifest file, pick the first one alphabetically when none have the `nyl.io/default-namespace: "true"` annotation</td><td></td><td></td><td>@NiklasRosenstein</td></tr>
|
|
12
|
+
<tr><td>Improvement</td><td>
|
|
13
|
+
|
|
14
|
+
Apply Nyl `PostProcessor` instructions at the end, after Nyl had a chance to fill in the manifest file's determined default namespace. Kyverno might add the `namespace: default` field to any resource that has no namespace set, making it impossbile for Nyl after the fact to tell which resources need to have their namespace injected.</td><td></td><td></td><td>@NiklasRosenstein</td></tr>
|
|
15
|
+
<tr><td>Fix</td><td>
|
|
16
|
+
|
|
17
|
+
Update `PostProcessor`, pointing Kyverno to a directory and expecting it to output all manifest, not just the mutated ones. The `PostProcessor` is now invoked at the very end, even after Nyl patches resources with the default namespace in the current manifest file.</td><td></td><td></td><td>@NiklasRosenstein</td></tr>
|
|
18
|
+
<tr><td>Fix</td><td>
|
|
19
|
+
|
|
20
|
+
fix #57 -- `ARGOCD_APP_NAMESPACE` and the `--default-namespace` option are used now only when no namespace is defined in the manifest file</td><td></td><td></td><td>@NiklasRosenstein</td></tr>
|
|
21
|
+
<tr><td>Improvement</td><td>
|
|
22
|
+
|
|
23
|
+
Resources generated by the Nyl `HelmChart` resource now get the chart resource's `metadata.namespace` populated before they are passed up and inlined into the rest of the manifest. Fixes #56</td><td></td><td></td><td>@NiklasRosenstein</td></tr>
|
|
24
|
+
<tr><td>Improvement</td><td>
|
|
25
|
+
|
|
26
|
+
Fix deprecation warnings of using the `loguru.logger.opt(ansi)` keyword argument and use the new `colors` kwarg instead</td><td></td><td></td><td>@NiklasRosenstein</td></tr>
|
|
27
|
+
<tr><td>Feature</td><td>
|
|
28
|
+
|
|
29
|
+
Add `PostProcessor.spec.kyvernoRules` field as a shorthand for defining Kyverno policies in a Nyl manifest.</td><td></td><td></td><td>@NiklasRosenstein</td></tr>
|
|
30
|
+
<tr><td>Refactor</td><td>
|
|
31
|
+
|
|
32
|
+
Refactor `PostProcessor` implementation for generating policy files and invoking Kyverno</td><td></td><td></td><td>@NiklasRosenstein</td></tr>
|
|
33
|
+
<tr><td>Improvement</td><td>
|
|
34
|
+
|
|
35
|
+
`PostProcessor` log for invoking Kyverno now lists the policy file paths that are going to be applied</td><td></td><td></td><td>@NiklasRosenstein</td></tr>
|
|
36
|
+
<tr><td>Fix</td><td>
|
|
37
|
+
|
|
38
|
+
`nyl new chart` now generates 2-space indented YAML and has a more complete template</td><td></td><td><a href="https://github.com/NiklasRosenstein/nyl/issues/47">47</a></td><td>@NiklasRosenstein</td></tr>
|
|
39
|
+
</table>
|
|
40
|
+
|
|
41
|
+
## 0.6.0
|
|
42
|
+
|
|
43
|
+
* Upgraded `argocd-cmp-server` in `nyl/argocd-cmp` container image to `v2.13.1` (see [#46](https://github.com/helsing-ai/nyl/pull/46))
|
|
44
|
+
* Re-introduce `settings.generate_placeholders` in `nyl-project.toml`, but warn if it is used. Enabling the option will have the
|
|
45
|
+
same effect as setting `on_lookup_failure = "CreatePlaceholder"` and take precedence over the original value of `on_lookup_failure`.
|
|
46
|
+
|
|
47
|
+
## 0.5.1
|
|
48
|
+
|
|
49
|
+
* Add Nix flake
|
|
50
|
+
* Docs: Add missing API docs for `nyl.secrets.kubernetes`
|
|
51
|
+
|
|
52
|
+
## 0.5.0
|
|
53
|
+
|
|
54
|
+
* Add the [`KubernetesSecret`](./reference/configuration/secrets.md#provider-kubernetessecret) secret provider
|
|
55
|
+
* Add the `ntyl secrets set` and `nyl secrets unset` commands
|
|
56
|
+
* Breaking: Replace the `settings.generate_placeholders` option with `settings.on_lookup_failure`
|
|
57
|
+
|
|
58
|
+
## 0.4.0
|
|
59
|
+
|
|
60
|
+
* Automatically replace the host in Kubeconfig `server` field if it is set to `localhost`, `0.0.0.0` or `127.0.0.1`
|
|
61
|
+
when a Kubeconfig is retrieved via SSH (saving you to configure `replace_apiserver_hostname` when sourcing a
|
|
62
|
+
Kubeconfig from a K3s/RKE2 cluster via SSH).
|
|
63
|
+
* Add `port` and `sudo` option to `KubeconfigFromSsh` config
|
|
64
|
+
|
|
65
|
+
## 0.3.0
|
|
66
|
+
|
|
67
|
+
* Add [`PostProcessor`](./reference/templating/inlining/postprocessor.md) inline resource which supports applying
|
|
68
|
+
Kyverno policies to the generated resources.
|
|
69
|
+
* Fixed a bug in the construction of the local Helm chart path when referencing a Helm chart in a Git repository.
|
|
@@ -7,4 +7,4 @@ resources in a cluster. Nyl provides basic support for ApplySets, allowing you t
|
|
|
7
7
|
and prune resources as they are removed from your configuration.
|
|
8
8
|
|
|
9
9
|
Note that ApplySet support is experimental and has still has various issues. You can following the progress of the
|
|
10
|
-
feature in the [nyl#5](https://github.com/
|
|
10
|
+
feature in the [nyl#5](https://github.com/helsing-ai/nyl/issues/5).
|
|
@@ -16,7 +16,7 @@ We recommend the following configuration:
|
|
|
16
16
|
repoServer:
|
|
17
17
|
extraContainers:
|
|
18
18
|
- name: nyl-v1
|
|
19
|
-
image: ghcr.io/
|
|
19
|
+
image: ghcr.io/helsing-ai/nyl/argocd-cmp:{{ NYL_VERSION }}
|
|
20
20
|
securityContext:
|
|
21
21
|
runAsNonRoot: true
|
|
22
22
|
runAsUser: 999
|
|
@@ -52,6 +52,9 @@ application, you would need to create a Helm chart that includes all the other c
|
|
|
52
52
|
complicated setup that is hard to maintain: It either requires you to repeat the same values in multiple places, or
|
|
53
53
|
all subcharts support `globals`.
|
|
54
54
|
|
|
55
|
+
The `HelmChart` generator populates its own Kubernetes namespace to that of its generated resources that lack a
|
|
56
|
+
namespace.
|
|
57
|
+
|
|
55
58
|
#### Secret injection
|
|
56
59
|
|
|
57
60
|
Natively, ArgoCD applications do not support injecting secrets into the Helm chart values. With Nyl, you can connect
|
|
@@ -6,14 +6,21 @@ not accept a `metadata` field.
|
|
|
6
6
|
|
|
7
7
|
## Prerequisites
|
|
8
8
|
|
|
9
|
-
|
|
9
|
+
You need the [`kyverno` CLI](https://kyverno.io/docs/kyverno-cli/) >1.13.x installed
|
|
10
|
+
|
|
11
|
+
!!! danger
|
|
12
|
+
In Kyverno 1.12.6, the `kyverno apply` command with the `-o` option outputs only the mutated resources. In
|
|
13
|
+
Kyverno 1.13.2, all resources are outputted. Nyl relies on the latter behavior.
|
|
10
14
|
|
|
11
15
|
## API Spec
|
|
12
16
|
|
|
13
17
|
```yaml
|
|
14
18
|
apiVersion: inline.nyl.io/v1
|
|
15
19
|
kind: PostProcessor
|
|
20
|
+
metadata:
|
|
21
|
+
name: my-post-processor
|
|
16
22
|
spec:
|
|
23
|
+
# Configure Kyverno policies to apply.
|
|
17
24
|
kyverno:
|
|
18
25
|
# A list of files that each contain a Kyverno policy resource, usually a `ClusterPolicy`. The paths are first
|
|
19
26
|
# considered relative to the manifest that this resource is defined in, and will then be searched in the project
|
|
@@ -29,7 +36,36 @@ spec:
|
|
|
29
36
|
kind: ClusterPolicy
|
|
30
37
|
metadata:
|
|
31
38
|
name: enforce-pod-security-context
|
|
32
|
-
spec:
|
|
39
|
+
spec:
|
|
40
|
+
rules:
|
|
41
|
+
- name: my-rule
|
|
42
|
+
match:
|
|
43
|
+
resources:
|
|
44
|
+
kinds:
|
|
45
|
+
- Pod
|
|
46
|
+
validate:
|
|
47
|
+
message: "Pod must have security context"
|
|
48
|
+
pattern:
|
|
49
|
+
spec:
|
|
50
|
+
securityContext:
|
|
51
|
+
runAsNonRoot: true
|
|
52
|
+
|
|
53
|
+
# Define rules for a single Kyverno `ClusterPolicy` to apply. The `name` field of the rule configuration may be
|
|
54
|
+
# ommited. Applies after policies defined in `kyverno`.
|
|
55
|
+
#
|
|
56
|
+
# To find more about Kyverno policies and rules, read https://kyverno.io/docs/writing-policies/.
|
|
57
|
+
kyvernoRules:
|
|
58
|
+
- match:
|
|
59
|
+
resources:
|
|
60
|
+
kinds:
|
|
61
|
+
- Service
|
|
62
|
+
mutate:
|
|
63
|
+
patchStrategicMerge:
|
|
64
|
+
spec:
|
|
65
|
+
(type): LoadBalancer
|
|
66
|
+
allocateLoadBalancerNodePorts: false
|
|
67
|
+
loadBalancerClass: ngrok
|
|
68
|
+
|
|
33
69
|
```
|
|
34
70
|
|
|
35
71
|
## Example
|
|
@@ -4,7 +4,7 @@ build-backend = "hatchling.build"
|
|
|
4
4
|
|
|
5
5
|
[project]
|
|
6
6
|
name = "nyl"
|
|
7
|
-
version = "0.
|
|
7
|
+
version = "0.7.0"
|
|
8
8
|
description = "Advanced templating engine for Kubernetes and GitOps."
|
|
9
9
|
authors = [
|
|
10
10
|
{name = "Niklas Rosenstein", email = "rosensteinniklas@gmail.com"},
|
|
@@ -40,3 +40,22 @@ dev-dependencies = [
|
|
|
40
40
|
"types-pyyaml>=6.0.12.20240311",
|
|
41
41
|
"types-requests>=2.32.0.20240712",
|
|
42
42
|
]
|
|
43
|
+
|
|
44
|
+
[tool.mypy]
|
|
45
|
+
explicit_package_bases = true
|
|
46
|
+
namespace_packages = true
|
|
47
|
+
show_column_numbers = true
|
|
48
|
+
strict = true
|
|
49
|
+
mypy_path = ["src"]
|
|
50
|
+
|
|
51
|
+
[tool.ruff]
|
|
52
|
+
line-length = 120
|
|
53
|
+
|
|
54
|
+
[tool.slap.test]
|
|
55
|
+
pytest = "uv run pytest ."
|
|
56
|
+
mypy = "uv run mypy ."
|
|
57
|
+
ruff-check = "uv run ruff check ."
|
|
58
|
+
ruff-fmt = "uv run ruff format --check ."
|
|
59
|
+
|
|
60
|
+
[tool.slap.run]
|
|
61
|
+
fmt = "uv run ruff format . && uv run ruff check --fix ."
|
|
@@ -79,7 +79,7 @@ def _callback(
|
|
|
79
79
|
logger.add(sys.stderr, level=LogLevel.ERROR.name if quiet else log_level.name, format=fmt)
|
|
80
80
|
if log_file:
|
|
81
81
|
logger.add(log_file, level=log_level.name, format=fmt)
|
|
82
|
-
logger.opt(
|
|
82
|
+
logger.opt(colors=True).debug("Nyl v{} run from <yellow>{}</>.", __version__, Path.cwd())
|
|
83
83
|
|
|
84
84
|
# Log some helpful information for debugging purposes.
|
|
85
85
|
logger.debug("Used command-line arguments: {}", lazy_str(pretty_cmd, sys.argv))
|
|
@@ -52,7 +52,11 @@ def chart(dir: Path) -> None:
|
|
|
52
52
|
dir,
|
|
53
53
|
"values.yaml",
|
|
54
54
|
"""
|
|
55
|
-
image:
|
|
55
|
+
image:
|
|
56
|
+
repository: my/image
|
|
57
|
+
tag: 1.0.0
|
|
58
|
+
pullPolicy: IfNotPresent
|
|
59
|
+
pullSecret: ""
|
|
56
60
|
""",
|
|
57
61
|
)
|
|
58
62
|
|
|
@@ -82,20 +86,25 @@ def chart(dir: Path) -> None:
|
|
|
82
86
|
apiVersion: apps/v1
|
|
83
87
|
kind: Deployment
|
|
84
88
|
metadata:
|
|
85
|
-
|
|
89
|
+
name: {{ .Release.Name }}
|
|
86
90
|
spec:
|
|
87
|
-
|
|
88
|
-
|
|
91
|
+
replicas: 1
|
|
92
|
+
selector:
|
|
89
93
|
matchLabels:
|
|
90
|
-
|
|
91
|
-
|
|
94
|
+
app.kubernetes.io/name: {{ .Release.Name }}
|
|
95
|
+
template:
|
|
92
96
|
metadata:
|
|
93
|
-
|
|
94
|
-
app: {{ .Release.Name }}
|
|
97
|
+
labels:
|
|
98
|
+
app.kubernetes.io/name: {{ .Release.Name }}
|
|
95
99
|
spec:
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
100
|
+
{{- if .Values.image.pullSecret }}
|
|
101
|
+
imagePullSecrets:
|
|
102
|
+
- name: {{ .Values.image.pullSecret }}
|
|
103
|
+
{{- end }}
|
|
104
|
+
containers:
|
|
105
|
+
- name: {{ .Release.Name }}
|
|
106
|
+
image: {{ .Values.image.repository }}:{{ .Values.image.tag }}
|
|
107
|
+
imagePullPolicy: {{ .Values.image.pullPolicy }}
|
|
99
108
|
""",
|
|
100
109
|
)
|
|
101
110
|
|
|
@@ -54,7 +54,7 @@ def run(
|
|
|
54
54
|
# Check if the context exists in the kubeconfig.
|
|
55
55
|
kubeconfig = Path(os.environ.get("KUBECONFIG", "~/.kube/config")).expanduser()
|
|
56
56
|
if not kubeconfig.is_file():
|
|
57
|
-
logger.opt(
|
|
57
|
+
logger.opt(colors=True).info("Profile <yellow>{}</> not found.", profile_name)
|
|
58
58
|
sys.exit(1)
|
|
59
59
|
|
|
60
60
|
try:
|
|
@@ -62,11 +62,11 @@ def run(
|
|
|
62
62
|
kubeconfig_data = _trim_to_context(kubeconfig_data, profile_name)
|
|
63
63
|
except ValueError:
|
|
64
64
|
logger.debug("Failed to parse the kubeconfig file/find context '{}'.", profile_name)
|
|
65
|
-
logger.opt(
|
|
65
|
+
logger.opt(colors=True).info("Profile <yellow>{}</> not found.", profile_name)
|
|
66
66
|
sys.exit(1)
|
|
67
67
|
else:
|
|
68
68
|
if not inherit_kubeconfig:
|
|
69
|
-
logger.opt(
|
|
69
|
+
logger.opt(colors=True).error(
|
|
70
70
|
"Found context <yellow>{}</> in the kubeconfig ({}), but no Nyl profile with that name. "
|
|
71
71
|
"Consider using --inherit-kubeconfig,-I to run the command in that Kubernetes context.",
|
|
72
72
|
profile_name,
|
|
@@ -74,7 +74,7 @@ def run(
|
|
|
74
74
|
)
|
|
75
75
|
sys.exit(1)
|
|
76
76
|
|
|
77
|
-
logger.opt(
|
|
77
|
+
logger.opt(colors=True).info(
|
|
78
78
|
"Falling back to context <yellow>{}</> from the kubeconfig ({}) due to --inherit-kubeconfig,-I option.",
|
|
79
79
|
profile_name,
|
|
80
80
|
kubeconfig,
|
|
@@ -89,7 +89,7 @@ def run(
|
|
|
89
89
|
kubeconfig.chmod(0o600)
|
|
90
90
|
|
|
91
91
|
profile = ActivatedProfile(kubeconfig)
|
|
92
|
-
logger.opt(
|
|
92
|
+
logger.opt(colors=True).info(
|
|
93
93
|
"Running command `<blue>{}</>` with {} <yellow>{}</>.",
|
|
94
94
|
lazy_str(pretty_cmd, command),
|
|
95
95
|
kind,
|