feat: bootstrap official runner through SPIFFE facade

This commit is contained in:
2026-09-20 20:00:34 +00:00
parent 5fdd39f7ff
commit 8b77b4be63
16 changed files with 470 additions and 28 deletions
+5 -3
View File
@@ -35,6 +35,7 @@ type PodManifest struct {
Image string
ServiceAccount string
Args []string
Environment map[string]string
}
// IdentityEntry is a ClusterStaticEntry pinned to one concrete Pod UID.
@@ -89,24 +90,25 @@ func (b Backend) Find(ctx context.Context, assignmentID string) (*taskworker.Exe
return executor(pods[0]), nil
}
func (b Backend) Create(ctx context.Context, assignment taskassignment.Assignment, metadata taskworker.Metadata) (*taskworker.Executor, error) {
func (b Backend) Create(ctx context.Context, assignment taskassignment.Assignment, launch taskworker.LaunchSpec) (*taskworker.Executor, error) {
if err := b.validate(); err != nil {
return nil, err
}
if assignment.Backend != taskassignment.BackendPod {
return nil, fmt.Errorf("Pod backend cannot create %q assignment", assignment.Backend)
}
labels := clone(metadata.Labels)
labels := clone(launch.Metadata.Labels)
labels["app.kubernetes.io/name"] = "gitea-dynamic-runner"
labels["app.kubernetes.io/component"] = "executor"
pod, err := b.API.CreatePod(ctx, PodManifest{
Name: assignment.ID,
Namespace: b.Config.Namespace,
Labels: labels,
Annotations: clone(metadata.Annotations),
Annotations: clone(launch.Metadata.Annotations),
Image: b.Config.Image,
ServiceAccount: b.Config.ServiceAccount,
Args: append(append([]string{}, b.Config.ExecutorArgs...), assignment.ID),
Environment: clone(launch.Environment),
})
if err != nil {
return nil, fmt.Errorf("create assignment Pod: %w", err)
+6 -1
View File
@@ -75,7 +75,9 @@ func TestFindRecoversPodByAssignmentLabel(t *testing.T) {
func TestCreateUsesDeterministicNameAndRecoveryMetadata(t *testing.T) {
api := &fakeAPI{}
metadata := taskworker.BackendMetadata(assignment())
executor, err := backend(api).Create(context.Background(), assignment(), metadata)
executor, err := backend(api).Create(context.Background(), assignment(), taskworker.LaunchSpec{
Metadata: metadata, Environment: map[string]string{"CI_RUNNER_CAPABILITY": "capability"},
})
if err != nil {
t.Fatal(err)
}
@@ -85,6 +87,9 @@ func TestCreateUsesDeterministicNameAndRecoveryMetadata(t *testing.T) {
if api.created.Annotations["ci.ddupan.top/spiffe-id"] != assignment().Identity.SPIFFEID {
t.Fatalf("annotations = %#v", api.created.Annotations)
}
if api.created.Environment["CI_RUNNER_CAPABILITY"] != "capability" {
t.Fatalf("environment = %#v", api.created.Environment)
}
if len(api.created.Args) != 2 || api.created.Args[1] != "gitea-task-42" || executor.IdentityTarget != "pod-uid" {
t.Fatalf("args=%v executor=%#v", api.created.Args, executor)
}
+5 -1
View File
@@ -59,6 +59,10 @@ func (c *Client) ListPods(ctx context.Context, namespace, selector string) ([]Po
}
func (c *Client) CreatePod(ctx context.Context, manifest PodManifest) (Pod, error) {
environment := make([]corev1.EnvVar, 0, len(manifest.Environment))
for name, value := range manifest.Environment {
environment = append(environment, corev1.EnvVar{Name: name, Value: value})
}
document := &corev1.Pod{
ObjectMeta: metav1.ObjectMeta{
Name: manifest.Name, Namespace: manifest.Namespace,
@@ -68,7 +72,7 @@ func (c *Client) CreatePod(ctx context.Context, manifest PodManifest) (Pod, erro
ServiceAccountName: manifest.ServiceAccount,
RestartPolicy: corev1.RestartPolicyNever,
Containers: []corev1.Container{{
Name: "executor", Image: manifest.Image, Args: manifest.Args,
Name: "executor", Image: manifest.Image, Args: manifest.Args, Env: environment,
SecurityContext: &corev1.SecurityContext{Privileged: boolPointer(true)},
VolumeMounts: []corev1.VolumeMount{{
Name: "spire-agent-socket", MountPath: "/run/spire/agent-sockets", ReadOnly: true,
+4 -1
View File
@@ -25,7 +25,7 @@ func TestClientPodLifecycleUsesTypedClient(t *testing.T) {
Name: "gitea-task-42", Namespace: "gitea-actions",
Labels: map[string]string{assignmentLabel: "gitea-task-42"},
Image: "zot/ci-executor:main", ServiceAccount: "gitea-task-executor",
Args: []string{"execute", "gitea-task-42"},
Args: []string{"execute", "gitea-task-42"}, Environment: map[string]string{"CI_RUNNER_CAPABILITY": "capability"},
})
if err != nil {
t.Fatal(err)
@@ -34,6 +34,9 @@ func TestClientPodLifecycleUsesTypedClient(t *testing.T) {
if err != nil {
t.Fatal(err)
}
if got := pod.Spec.Containers[0].Env; len(got) != 1 || got[0].Name != "CI_RUNNER_CAPABILITY" || got[0].Value != "capability" {
t.Fatalf("environment = %#v", got)
}
pod.UID = types.UID("pod-uid")
pod.Status.Phase = corev1.PodRunning
if _, err := client.Kubernetes.CoreV1().Pods("gitea-actions").Update(context.Background(), pod, metav1.UpdateOptions{}); err != nil {