Gitea is an open source, self hosted git repository with a powerful web UI. In the following short tutorial I will explain (and remember myself) how to setup Gitea on self managed Kubernetes cluster. If you do not yet have a Kubernetes cluster take a look to the Imixs-Cloud project.
The Deployment
Gitea comes with a official docker image. Gitea supports a Helm Chart but personally I am not a fried of Helm so I use the native deployment strategy with yaml files. For the deployment I use 3 yaml files to separate the setup configuration – which is a good practice:
- 010-deployment.yaml
- 020-volumes.yaml
- 030-network.yaml
010-deployment.yaml
The deployment.yaml file is quite easy:
###################################################
# Namespace Gitea
###################################################
apiVersion: v1
kind: Namespace
metadata:
name: gitea-repo
###############################
# Deplyoment Gitea
###############################
---
apiVersion: apps/v1
kind: Deployment
metadata:
name: gitea
namespace: gitea-repo
labels:
app: gitea
spec:
replicas: 1
selector:
matchLabels:
app: gitea
template:
metadata:
labels:
app: gitea
spec:
containers:
- name: gitea
image: gitea/gitea:1.13.2
ports:
- containerPort: 3000
name: gitea
- containerPort: 22
name: git-ssh
volumeMounts:
- mountPath: /data
name: git-data
volumes:
- name: git-data
persistentVolumeClaim:
claimName: git-pvc
Gitea exposes the ports 3000 for HTTP and the SSH port 20.
020-volumes.yaml
As you can see I use a persistent volume with the name ‘git-data’ to map the /data folder of Gitea to a Kubernetes volume. If you don’t have yet a distributed storage solution in your Kubernetes cluster take again a look into the section ‘Storage’ of the Imixs-Cloud project.
The yaml file looks like this:
---
###################################################
# Persistence Volume Claim
###################################################
kind: PersistentVolume
apiVersion: v1
metadata:
name: git-pv
namespace: gitea-repo
spec:
capacity:
storage: 5Gi
volumeMode: Filesystem
accessModes:
- ReadWriteOnce
claimRef:
namespace: gitea-repo
name: git-pvc
csi:
driver: driver.longhorn.io
fsType: ext4
volumeHandle: git-data
storageClassName: longhorn-durable
---
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: git-pvc
namespace: gitea-repo
spec:
accessModes:
- ReadWriteOnce
storageClassName: longhorn-durable
resources:
requests:
storage: 5Gi
volumeName: "git-pv"
Here I define a persistence volume of 5Gi with a durable storage class. Please edit the volume configuration according to your Kubernetes environment. I will not discuss volumes in this tutorial.
030-network.yaml
Finally we need a network configuration consisting of the services to be exposes and a ingress configuration:
###############################
# Service
###############################
---
kind: Service
apiVersion: v1
metadata:
name: gitea-service
namespace: gitea-repo
spec:
selector:
app: gitea
ports:
- name: gitea-http
port: 3000
- name: gitea-ssh
port: 22
---
###################################################
# Ingress
###################################################
kind: Ingress
apiVersion: networking.k8s.io/v1
metadata:
name: git-tls
namespace: gitea-repo
annotations:
cert-manager.io/cluster-issuer: "letsencrypt-prod"
spec:
tls:
- hosts:
- gitea.foo.com
secretName: tls-gitea
rules:
- host: gitea.foo.com
http:
paths:
- path: /
pathType: Prefix
backend:
service:
name: gitea-service
port:
number: 3000
Here I expose the port 3000 (http) as an ingress. I use the kubernetes nginx controller and Let’s Encrypt for the ingress. Again you can find description how to use NGINX and Let’s Encrypt in the section ‘NGNIX of the Imixs-Cloud project.
Replace the ‘gita.foo.com’ dns name with your own public internet host name.
Run it…
Now all configuration is ready and we can start the deployment using kubectl:
kubectl apply -f ./your-gitea-config/
Now you should be able to can access your gitea repo from your web browser!
Customizing
Gitea offers many ways to customize the UI and functionality. Most of the configuration can be done in the property file /data/gitea/conf/app.ini . You can find a complete list of properties and options in the Gitea Cheat Sheet . To change the app.ini file first do a ssh into your gitea pod. From inside the pod you can use the vi editor to edit the file. First make a backup:
$ cp /data/gitea/conf/app.ini /data/gitea/conf/app.backup
$ vi /data/gitea/conf/app.ini
After you have changed and saved the file you need to restart the POD.
SSH
Finally I will explain how to enable SSH for the git repo. This step in optional.
I assume that you use the NGINX Ingress Controller. In its default setup the controller listens to the port 80, 443 and 8443. But not to ssh port 22.
Background: an Ingress is specifically for virtual-hosting using the header of the incoming request to know which backend to use. There is no such mechanism in SSH. However, the NGINX Ingress controller supports TCP and UDP services as long as you can assign a dedicated port for them (which we can do in our case). Via a ConfigMap we can configure which port on the ingress controller to map to the port on the Gitea service. Than we can expose the port to the internet. Find details here.
To avoid using port 22 I change the configuration of the Gitea SSH port to 2222.
In the following patch configuration I tell the NGINX Ingress Controller to listen on port 2222 :
spec:
template:
spec:
containers:
- name: controller
# defind cusotm tcp/udp configmap
args:
- --tcp-services-configmap=$(POD_NAMESPACE)/tcp-configmap-giteassh
ports:
- name: ssh
containerPort: 2222
protocol: TCP
This patch also apples the configmap ‘tcp-configmap-giteassh’. The config map looks like this:
apiVersion: v1
kind: ConfigMap
metadata:
name: tcp-configmap-giteassh
namespace: gitea-repo
data:
2222: "gitea-repo/gitea-service:2222"
See also the discussion here.
My Personal Conclusion
Finally I come to the conclusion that running gitea on Kubernetes did not really work with the NGINX Ingress Controller. You need to do different tweaks in the controller. Because I use git also for my kubernetes configuration I run Gitea on a separate virtual cloud server outside of my cluster to make these things independent from each other.
Read my tutorial Running Gitea on a Virtual Cloud Server to see how you can setup Gitea in a few minutes on a internet cloud server using Docker.
Hello,
Thanks by the tutorial, in this case is not neccesary bind the timezone/localtime like docker?
https://docs.gitea.io/en-us/install-with-docker/#mysql-database
Best regards,