<?xml version="1.0" encoding="utf-8" standalone="yes"?><rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom"><channel><title>Talos on Simon Shine</title><link>https://simonshine.dk/tags/talos/</link><description>Recent content in Talos on Simon Shine</description><generator>Hugo</generator><language>en-us</language><lastBuildDate>Sun, 08 Nov 2026 00:07:52 +0100</lastBuildDate><atom:link href="https://simonshine.dk/tags/talos/index.xml" rel="self" type="application/rss+xml"/><item><title>OIDC kubeconfigs with Zitadel</title><link>https://simonshine.dk/articles/oidc-kubeconfigs-with-zitadel/</link><pubDate>Sun, 08 Nov 2026 00:07:52 +0100</pubDate><guid>https://simonshine.dk/articles/oidc-kubeconfigs-with-zitadel/</guid><description>&lt;p&gt;Kubeconfig that outlive the persons holding it are a compliance anti-pattern.&lt;/p&gt;
&lt;p&gt;&lt;a href="https://zitadel.com/"&gt;Zitadel&lt;/a&gt; can be the issuer instead: &lt;code&gt;kubectl&lt;/code&gt; opens a browser, gets a short-lived token,
and the API server maps a project role to a Kubernetes group.&lt;/p&gt;
&lt;p&gt;&lt;em&gt;(Zitadel is a modern replacement for Keycloak. You can use Keycloak for all of this, too.)&lt;/em&gt;&lt;/p&gt;
&lt;p&gt;From a fresh cluster:&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;vendor and deploy Zitadel,&lt;/li&gt;
&lt;li&gt;create one project role,&lt;/li&gt;
&lt;li&gt;point &lt;code&gt;kubectl&lt;/code&gt; at the OIDC app.&lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id="vendor-and-deploy-zitadel"&gt;
 Vendor and deploy Zitadel
 &lt;a class="heading-anchor" href="#vendor-and-deploy-zitadel" aria-label="Link to this section"&gt;&amp;para;&lt;/a&gt;
&lt;/h2&gt;
&lt;p&gt;Vendor the Zitadel chart &lt;a href="https://simonshine.dk/articles/helm-vendor-vendoring-helm-charts-with-nix"&gt;using the &lt;code&gt;helm-vendor&lt;/code&gt; CLI&lt;/a&gt;:&lt;/p&gt;</description></item><item><title>Evaluating the Kubernetes-native Forgejo CI runners</title><link>https://simonshine.dk/articles/evaluating-the-kubernetes-native-forgejo-ci-runners/</link><pubDate>Sun, 25 Oct 2026 13:19:41 +0100</pubDate><guid>https://simonshine.dk/articles/evaluating-the-kubernetes-native-forgejo-ci-runners/</guid><description>&lt;p&gt;Until 9 October, CI for my &lt;a href="https://forgejo.org"&gt;Forgejo&lt;/a&gt; ran in docker-in-docker: &lt;a href="https://code.forgejo.org/forgejo/runner"&gt;forgejo-runner&lt;/a&gt; 6.3.1
with a privileged &lt;code&gt;docker:29.3.1-dind&lt;/code&gt; sidecar, three replicas. Since then every job runs as a
Kubernetes Job, through the execution-backend protocol that &lt;a href="https://code.forgejo.org/forgejo/runner/releases/tag/v13.1.0"&gt;forgejo-runner v13.1.0&lt;/a&gt; added on
31 August.&lt;/p&gt;
&lt;p&gt;A few people have asked what that is like to run for real. Two weeks and 54 tasks in, this is
what I know. The Forgejo side of the same cluster is in &lt;a href="https://simonshine.dk/articles/running-forgejo-on-a-hetzner-kubernetes-cluster"&gt;Running Forgejo on a Hetzner Kubernetes
cluster&lt;/a&gt;.&lt;/p&gt;</description></item><item><title>Running Forgejo on a Hetzner Kubernetes cluster</title><link>https://simonshine.dk/articles/running-forgejo-on-a-hetzner-kubernetes-cluster/</link><pubDate>Sun, 25 Oct 2026 13:00:29 +0100</pubDate><guid>https://simonshine.dk/articles/running-forgejo-on-a-hetzner-kubernetes-cluster/</guid><description>&lt;p&gt;I host my own git. Since May 2026 that has been a single &lt;a href="https://forgejo.org"&gt;Forgejo&lt;/a&gt; pod on a Talos cluster at
Hetzner, deployed from Nix with &lt;a href="https://github.com/hall/kubenix"&gt;kubenix&lt;/a&gt; and the upstream &lt;a href="https://code.forgejo.org/forgejo-helm/forgejo-helm"&gt;forgejo-helm&lt;/a&gt; chart.&lt;/p&gt;
&lt;p&gt;The first deploy was Forgejo 14.0.4 on chart 16.2.2, SQLite, and a 20Gi volume. Five months later
it runs on Postgres, has been knocked over by crawlers three times. Most of what changed in the
deployment came from those outages.&lt;/p&gt;
&lt;h2 id="tldr"&gt;
 tl;dr
 &lt;a class="heading-anchor" href="#tldr" aria-label="Link to this section"&gt;&amp;para;&lt;/a&gt;
&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;The chart is vendored and pinned in &lt;code&gt;charts.toml&lt;/code&gt;; kubenix renders it with &lt;code&gt;chart2json&lt;/code&gt;, so the
Helm values are a Nix attrset and &lt;code&gt;nix build .#test&lt;/code&gt; asserts on the output.&lt;/li&gt;
&lt;li&gt;No OAuth client secret is in git. A Job generates it into Vault, and VSO renders it back.&lt;/li&gt;
&lt;li&gt;A runner that registers on every pod start from an &lt;code&gt;emptyDir&lt;/code&gt; leaves three offline rows per
rollout. I have 29 of them.&lt;/li&gt;
&lt;li&gt;A crawler walking every ref of one repository in every archive format put 16.2G of tarballs on a
20Gi volume. Source archives are now off.&lt;/li&gt;
&lt;li&gt;A crawler on &lt;code&gt;blame&lt;/code&gt;, &lt;code&gt;commit&lt;/code&gt;, &lt;code&gt;commits&lt;/code&gt; and &lt;code&gt;src&lt;/code&gt; pages took the Actions API down, and three
release runs were recorded as failures while their steps passed. An Envoy Gateway rate limit of
60 a minute on those paths fixed it.&lt;/li&gt;
&lt;li&gt;Hetzner volumes only grow. Going from 40Gi to 10Gi was a new claim, a &lt;code&gt;tar&lt;/code&gt; pipe, and a sha256
over all 3638 files.&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id="the-chart-is-a-directory"&gt;
 The chart is a directory
 &lt;a class="heading-anchor" href="#the-chart-is-a-directory" aria-label="Link to this section"&gt;&amp;para;&lt;/a&gt;
&lt;/h2&gt;
&lt;p&gt;The chart is vendored with &lt;code&gt;helm-vendor&lt;/code&gt;, a small CLI of mine that keeps a registry in
&lt;code&gt;charts.toml&lt;/code&gt; and unpacks each chart into &lt;code&gt;charts/&lt;/code&gt;. Forgejo publishes its chart only as an OCI
artifact:&lt;/p&gt;</description></item><item><title>Managing Secrets privately with sops-nix</title><link>https://simonshine.dk/articles/managing-secrets-privately-with-sops-nix/</link><pubDate>Fri, 15 May 2026 02:37:41 +0200</pubDate><guid>https://simonshine.dk/articles/managing-secrets-privately-with-sops-nix/</guid><description>&lt;h2 id="tldr"&gt;
 tl;dr
 &lt;a class="heading-anchor" href="#tldr" aria-label="Link to this section"&gt;&amp;para;&lt;/a&gt;
&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;I want to commit my secrets encrypted to git with &lt;a href="https://github.com/Mic92/sops-nix"&gt;sops-nix&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;I want to publish my infra-as-code, but don&amp;rsquo;t want to publish my git secrets&lt;/li&gt;
&lt;li&gt;So I put my secrets in a private &lt;code&gt;git+file&lt;/code&gt; flake input&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id="motivation"&gt;
 Motivation
 &lt;a class="heading-anchor" href="#motivation" aria-label="Link to this section"&gt;&amp;para;&lt;/a&gt;
&lt;/h2&gt;
&lt;p&gt;I run Kubernetes clusters managed declaratively with &lt;a href="https://www.talos.dev/"&gt;Talos Linux&lt;/a&gt; and &lt;a href="https://github.com/hall/kubenix"&gt;kubenix&lt;/a&gt;. I want to publish the entire repository that defines the cluster. It includes commands that require authentication (&lt;code&gt;kubectl&lt;/code&gt;, &lt;code&gt;talosctl&lt;/code&gt;, &lt;code&gt;hcloud&lt;/code&gt;, etc.) that don&amp;rsquo;t work without their secrets.&lt;/p&gt;</description></item><item><title>NixOS runners on Forgejo Actions</title><link>https://simonshine.dk/articles/forgejo-actions-nixos-runners/</link><pubDate>Thu, 23 Apr 2026 22:06:40 +0200</pubDate><guid>https://simonshine.dk/articles/forgejo-actions-nixos-runners/</guid><description>&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Note:&lt;/strong&gt; You can see the project in action here: &lt;a href="https://git.shine.town/infra/runners"&gt;https://git.shine.town/infra/runners&lt;/a&gt;&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;I decided to bootstrap a Kubernetes cluster with &lt;a href="https://www.talos.dev/"&gt;Talos&lt;/a&gt; and
&lt;a href="https://kubenix.org/"&gt;kubenix&lt;/a&gt; during my vacation.&lt;/p&gt;
&lt;p&gt;A lot of experience came out of that, and I&amp;rsquo;m trying to unpack it gradually.&lt;/p&gt;
&lt;p&gt;One of the things I host on this cluster is &lt;a href="https://forgejo.org/"&gt;Forgejo&lt;/a&gt;, which is
&lt;a href="https://codeberg.org/"&gt;Codeberg&lt;/a&gt;&amp;rsquo;s fork of Gitea. Forgejo has &lt;a href="https://forgejo.org/docs/next/user/actions/reference/"&gt;Forgejo
Actions&lt;/a&gt; which is a CI system that mimicks
GitHub Actions, and it has a &lt;a href="https://forgejo.org/docs/next/user/packages/container/"&gt;Container Registry&lt;/a&gt;
much like GHCR, or DockerHub.&lt;/p&gt;</description></item></channel></rss>