Skip to content

Commit ef5f673

Browse files
committed
feat: implements Activityworker CRD and Controller
1 parent 1a77783 commit ef5f673

24 files changed

Lines changed: 1007 additions & 214 deletions

‎PROJECT‎

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,4 +18,13 @@ resources:
1818
kind: Activity
1919
path: algatux.dev/kube-activity-engine/api/v1beta1
2020
version: v1beta1
21+
- api:
22+
crdVersion: v1
23+
namespaced: true
24+
controller: true
25+
domain: algatux.dev
26+
group: kube-activity-engine
27+
kind: ActivityWorker
28+
path: algatux.dev/kube-activity-engine/api/v1beta1
29+
version: v1beta1
2130
version: "3"

‎README.md‎

Lines changed: 97 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -4,23 +4,46 @@ A Kubernetes operator for managing Activity resources with distributed worker ex
44

55
## Overview
66

7-
KubeActivityEngine is a Kubernetes controller that manages custom `Activity` resources. It provides a framework for orchestrating activities with configurable inputs and tracking the status of multiple workers executing those activities. The operator maintains state information for each worker (READY, RUNNING, COMPLETED, FAILED) and provides a declarative way to manage distributed activity execution in Kubernetes clusters.
7+
KubeActivityEngine is a Kubernetes operator that manages custom `Activity` and `ActivityWorker` resources. It provides a framework for orchestrating activities with configurable inputs and automatically creating workers to execute those activities. When an Activity enters the Initialization state, the controller creates ActivityWorker resources that define job specifications. The operator provides a declarative way to manage distributed activity execution in Kubernetes clusters with full lifecycle tracking.
88

99
## Features
1010

11-
- **Custom Resource Definition (CRD)**: Define activities as Kubernetes resources
11+
- **Dual Custom Resource Definitions (CRDs)**: Define activities and workers as Kubernetes resources
12+
- **Activity CRD**: Orchestrates activity lifecycle with configurable inputs
13+
- **ActivityWorker CRD**: Defines job specifications with ActivityJob structure
14+
- **Automatic Worker Creation**: Controller automatically creates ActivityWorker resources during Activity initialization
15+
- **Flexible Job Configuration**: ActivityJob spec supports custom images, commands, args, environment variables, and pull policies
1216
- **Worker Status Tracking**: Monitor the state of multiple workers processing activities
13-
- **Configurable Inputs**: Pass key-value input parameters to activities
1417
- **Kubernetes-Native**: Built using the Kubebuilder framework with full Kubernetes API integration
1518
- **Status Conditions**: Track activity lifecycle with standard Kubernetes condition types
1619
- **RBAC Support**: Fine-grained access control with admin, editor, and viewer roles
1720

1821
## Architecture
1922

20-
The operator watches for `Activity` custom resources and manages their lifecycle. Each Activity resource contains:
23+
The operator manages two custom resource types that work together:
2124

22-
- **Spec**: Desired state including activity name and input parameters
23-
- **Status**: Observed state with worker statuses and conditions
25+
### Activity Resource
26+
27+
The `Activity` CRD represents a unit of work to be executed. Each Activity contains:
28+
29+
- **Spec**: Desired state including activity name and input parameters (key-value pairs)
30+
- **Status**: Observed state with conditions tracking the activity lifecycle
31+
32+
When an Activity is created and reaches the "Initialization" condition state, the controller automatically creates ActivityWorker resources.
33+
34+
### ActivityWorker Resource
35+
36+
The `ActivityWorker` CRD defines the execution specification for workers. Each ActivityWorker contains:
37+
38+
- **Spec**: Job specification using the `ActivityJob` structure
39+
- **Name**: Unique identifier for the job
40+
- **Image**: Container image to run (e.g., `bash:5.0`)
41+
- **Command**: Command array to execute (e.g., `["bash", "-c"]`)
42+
- **Args**: Arguments array for the command (e.g., `["echo done!"]`)
43+
- **Env**: Environment variables for the container
44+
- **ImagePullPolicy**: Pull policy for the container image
45+
- **Status**: Observed state with conditions tracking the worker lifecycle
46+
- **Labels**: Automatically labeled with `kube-activity-engine.algatux.dev/activity` to link to parent Activity
2447

2548
### Activity States
2649

@@ -108,6 +131,48 @@ View detailed information:
108131
kubectl describe activity my-activity
109132
```
110133

134+
### Quick Demo
135+
136+
After applying an Activity, the controller automatically creates an **ActivityWorker** resource that defines a job specification. The ActivityWorker uses the new `ActivityJob` CRD structure:
137+
138+
**Default ActivityJob Configuration:**
139+
- **Image**: `bash:5.0`
140+
- **Command**: `["bash", "-c"]`
141+
- **Args**: `["echo done!"]`
142+
- **Environment**: `TEST=FAKE` (example environment variable)
143+
- **ImagePullPolicy**: `IfNotPresent`
144+
145+
**Verify the created resources:**
146+
147+
List ActivityWorkers for your activity:
148+
```sh
149+
kubectl get activityworkers -l kube-activity-engine.algatux.dev/activity=my-activity
150+
```
151+
152+
View ActivityWorker details:
153+
```sh
154+
kubectl describe activityworker <worker-name>
155+
```
156+
157+
Check the ActivityWorker spec:
158+
```sh
159+
kubectl get activityworker <worker-name> -o yaml
160+
```
161+
162+
**Expected Output:**
163+
The ActivityWorker will show the job configuration including the bash command that echoes "done!". The worker's status conditions will track its lifecycle state.
164+
165+
**Troubleshooting the demo:**
166+
- If no ActivityWorkers are created, check the Activity status conditions:
167+
```sh
168+
kubectl get activity my-activity -o jsonpath='{.status.conditions}'
169+
```
170+
- Check the controller logs for any errors:
171+
```sh
172+
kubectl logs -n kubeactivityengine-system deployment/kubeactivityengine-controller-manager
173+
```
174+
- Verify that the Activity has the "Initialization" condition set to "True"
175+
111176
### Checking Worker Status
112177

113178
Monitor the status of workers processing your activity:
@@ -196,26 +261,41 @@ The chart will be available in `dist/chart/`. Use `--force` flag when updating i
196261
## Project Structure
197262

198263
```
199-
├── api/v1beta1/ # API definitions
200-
│ └── activity_types.go # Activity CRD types
201-
├── internal/controller/ # Controller implementations
202-
│ └── activity_controller.go # Activity reconciler
203-
├── config/ # Kubernetes manifests
204-
│ ├── crd/ # CRD definitions
205-
│ ├── rbac/ # RBAC configurations
206-
│ ├── samples/ # Example resources
207-
│ └── manager/ # Controller deployment
208-
└── cmd/ # Application entrypoint
264+
├── api/v1beta1/ # API definitions
265+
│ ├── activity_types.go # Activity CRD types
266+
│ ├── activityworker_types.go # ActivityWorker CRD types (includes ActivityJob spec)
267+
│ └── states/ # State type definitions
268+
├── internal/
269+
│ ├── controller/ # Controller implementations
270+
│ │ ├── activity_controller.go # Activity reconciler
271+
│ │ └── activityworker_controller.go # ActivityWorker reconciler
272+
│ └── state_machine/ # State machine logic
273+
│ ├── activity_state_machine.go # Handler retrieval logic
274+
│ └── transitions/ # State transition handlers
275+
│ ├── initialization.go # Initialization state handler (creates ActivityWorkers)
276+
│ └── empty_conditions.go # Initial state handler
277+
├── config/ # Kubernetes manifests
278+
│ ├── crd/ # CRD definitions
279+
│ ├── rbac/ # RBAC configurations
280+
│ ├── samples/ # Example resources
281+
│ └── manager/ # Controller deployment
282+
└── cmd/ # Application entrypoint
209283
```
210284

211285
## RBAC Roles
212286

213-
The operator provides three predefined roles:
287+
The operator provides predefined roles for both Activity and ActivityWorker resources:
214288

289+
**Activity Roles:**
215290
- **activity-admin-role**: Full access to Activity resources
216291
- **activity-editor-role**: Create, update, and delete activities
217292
- **activity-viewer-role**: Read-only access to activities
218293

294+
**ActivityWorker Roles:**
295+
- **activityworker-admin-role**: Full access to ActivityWorker resources
296+
- **activityworker-editor-role**: Create, update, and delete activity workers
297+
- **activityworker-viewer-role**: Read-only access to activity workers
298+
219299
## Contributing
220300

221301
We welcome contributions! To contribute:

‎api/v1beta1/activity_types.go‎

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@ import (
2424
type ActivityInputs map[string]string
2525
type ActivityWorkersStatus map[string]ActivityWorkerStatus
2626

27-
type ActivityWorkerStatus struct {
27+
type ActivityWorkerRefs struct {
2828
Id string `json:"id"`
2929
Status states.ActivityWorkerState `json:"status"`
3030
}
@@ -70,7 +70,7 @@ type ActivityStatus struct {
7070
Conditions []metav1.Condition `json:"conditions,omitempty"`
7171

7272
// ActivityWorkerStatuses
73-
WorkersStatus ActivityWorkersStatus `json:"workersStatus,omitempty"`
73+
WorkersStatus []ActivityWorkerRefs `json:"workersStatus,omitempty"`
7474
}
7575

7676
// +kubebuilder:object:root=true
Lines changed: 97 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,97 @@
1+
/*
2+
Copyright 2025.
3+
4+
Licensed under the Apache License, Version 2.0 (the "License");
5+
you may not use this file except in compliance with the License.
6+
You may obtain a copy of the License at
7+
8+
http://www.apache.org/licenses/LICENSE-2.0
9+
10+
Unless required by applicable law or agreed to in writing, software
11+
distributed under the License is distributed on an "AS IS" BASIS,
12+
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
See the License for the specific language governing permissions and
14+
limitations under the License.
15+
*/
16+
17+
package v1beta1
18+
19+
import (
20+
v1 "k8s.io/api/core/v1"
21+
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
22+
)
23+
24+
// EDIT THIS FILE! THIS IS SCAFFOLDING FOR YOU TO OWN!
25+
// NOTE: json tags are required. Any new fields you add must have json tags for the fields to be serialized.
26+
27+
type ActivityJob struct {
28+
Name string `json:"name"`
29+
Image string `json:"image"`
30+
Command []string `json:"command"`
31+
Args []string `json:"args"`
32+
Env []v1.EnvVar `json:"env"`
33+
ImagePullPolicy v1.PullPolicy `json:"imagePullPolicy"`
34+
}
35+
36+
// ActivityWorkerSpec defines the desired state of ActivityWorker
37+
type ActivityWorkerSpec struct {
38+
// More info: https://book.kubebuilder.io/reference/markers/crd-validation.html
39+
40+
Job *ActivityJob `json:"job"`
41+
}
42+
43+
// ActivityWorkerStatus defines the observed state of ActivityWorker.
44+
type ActivityWorkerStatus struct {
45+
// INSERT ADDITIONAL STATUS FIELD - define observed state of cluster
46+
// Important: Run "make" to regenerate code after modifying this file
47+
48+
// For Kubernetes API conventions, see:
49+
// https://github.com/kubernetes/community/blob/master/contributors/devel/sig-architecture/api-conventions.md#typical-status-properties
50+
51+
// conditions represent the current state of the ActivityWorker resource.
52+
// Each condition has a unique type and reflects the status of a specific aspect of the resource.
53+
//
54+
// Standard condition types include:
55+
// - "Available": the resource is fully functional
56+
// - "Progressing": the resource is being created or updated
57+
// - "Degraded": the resource failed to reach or maintain its desired state
58+
//
59+
// The status of each condition is one of True, False, or Unknown.
60+
// +listType=map
61+
// +listMapKey=type
62+
// +optional
63+
Conditions []metav1.Condition `json:"conditions,omitempty"`
64+
}
65+
66+
// +kubebuilder:object:root=true
67+
// +kubebuilder:subresource:status
68+
69+
// ActivityWorker is the Schema for the activityworkers API
70+
type ActivityWorker struct {
71+
metav1.TypeMeta `json:",inline"`
72+
73+
// metadata is a standard object metadata
74+
// +optional
75+
metav1.ObjectMeta `json:"metadata,omitempty,omitzero"`
76+
77+
// spec defines the desired state of ActivityWorker
78+
// +required
79+
Spec ActivityWorkerSpec `json:"spec"`
80+
81+
// status defines the observed state of ActivityWorker
82+
// +optional
83+
Status ActivityWorkerStatus `json:"status,omitempty,omitzero"`
84+
}
85+
86+
// +kubebuilder:object:root=true
87+
88+
// ActivityWorkerList contains a list of ActivityWorker
89+
type ActivityWorkerList struct {
90+
metav1.TypeMeta `json:",inline"`
91+
metav1.ListMeta `json:"metadata,omitempty"`
92+
Items []ActivityWorker `json:"items"`
93+
}
94+
95+
func init() {
96+
SchemeBuilder.Register(&ActivityWorker{}, &ActivityWorkerList{})
97+
}

0 commit comments

Comments
 (0)