With many projects on GitHub, the CI/CD bills finally reached a point where I couldn’t ignore the cost anymore. I decided it was time to move the operation in-house and build my own pipeline.
I settled on Gitea paired with its native Actions runners. To be honest, it wasn't exactly a "plug-and-play" experience. I had to navigate a hybrid setup involving dedicated VMs and Docker containers. But the result was worth the friction.
I’m not going to bore you with a step-by-step tutorial. Between documentation and LLMs, you can find the specific commands for your OS easily. Instead, I want to talk about the architecture and the "why" behind it. In the age of AI, the hard part isn't writing the code; it’s knowing what’s possible and asking the right questions to get there.
Typical CI/CD pipeline
```mermaid
graph LR
subgraph Development
A[Plan] --> B[Develop]
end
subgraph "CI Pipeline"
B --> C[Commit]
C --> D[Build]
D --> E[Test]
end
subgraph "CD Pipeline"
E --> F[Deploy]
F --> G[Operate]
end
%% Styling
style G fill:#f96,stroke:#333,stroke-width:2px
style C fill:#bbf,stroke:#333
```
Overview
Ultimately, the architecture boils down to this:```mermaid
graph TD
subgraph Control_Center [Central Server]
Gitea[Gitea Instance]
end
subgraph Build_Farm [Dedicated Runner Nodes]
Gitea -- "Job Dispatch" --> Linux[Linux Box]
Gitea -- "Job Dispatch" --> Win[Windows Box]
Gitea -- "Job Dispatch" --> Mac[Mac Studio/Mini]
end
%% Styling for clarity
style Gitea fill:#62943e,color:#fff,stroke:#333
style Linux fill:#f1f1f1,stroke:#333
style Win fill:#f1f1f1,stroke:#333
style Mac fill:#f1f1f1,stroke:#333
```
PoC will be```mermaid
graph TD
subgraph Host_Machine [Host Environment]
subgraph Docker_Network [Docker Engine]
Server[Gitea Server Container]
L_Runner[Linux Runner Container]
end
subgraph Virtual_Layer [Hypervisor / VM]
subgraph Win_VM [Windows VM]
W_Runner[Windows Runner]
end
subgraph Mac_VM [macOS VM]
M_Runner[macOS Runner]
end
end
Server <--> L_Runner
Server <--> W_Runner
Server <--> M_Runner
end
%% Styling
style Server fill:#62943e,color:#fff
style Docker_Network stroke-dasharray: 5 5
style Virtual_Layer stroke-dasharray: 5 5
```
-->-->-->