openstack-infrastructure-te.../s2i2s/forgejo/README.md

4.8 KiB

Forgejo (git service) of the S2I2S project

One VM, m1.xlarge (RAM 16 - VCPUs 8), Ubuntu 24.04, 20 GB of root disk, with two interfaces:

Interface Address Use
main private network 10.10.0.165 traffic from the L7 HAPROXY load balancers, administration, monitoring
postgresql-srv-net from the DHCP pool the only way to the database

and one 200 GB SSD volume (CephSSD, enable_online_resize) on /dev/vdb, for the repositories and the attachments.

The resources live in ../../modules/forgejo, which also carries the sizing and the service ports as defaults, so another project can instantiate it with a handful of lines. (The first version of this workspace declared the resources inline, like s2i2s/mailbackup-relay does: they were moved into a module when the sizing of the services was moved out of ../variables.)

Only what belongs to this project is set in main.tf: the address on the main private network, which comes from the address plan in ../variables (basic_services_ip.forgejo), and the IDs read from the other workspaces.

Security groups on the ports:

  • default_for_all and traffic_to_forgejo_from_the_main_load_balancers on the main network port. The second one opens forgejo_server_data.service_ports (3000, see below) from each L7 load balancer: change that list if the service listens elsewhere.
  • vm_access_to_the_postgresql_service, taken from the postgresql workspace, on the port in the dedicated network of the database.

Names

Name Type Managed here
forgejo.s2i2s.cloud.isti.cnr.it A → 10.10.0.165 yes, internal name used by the playbooks and by the load balancer
git.s2i2s.cloud.isti.cnr.it CNAME → main-lb.s2i2s.cloud.isti.cnr.it. yes
gitea-s2i2s.isti.cnr.it the name of the service being migrated no: it lives in the isti.cnr.it zone and is moved by hand at the migration

Both public names are served by the L7 load balancers: the forgejo entry of haproxy_l7_services in group_vars/main_haproxy_l7/main_haproxy_l7.yml of infrastructure-playbooks sends them to 10.10.0.165:3000.

TLS: no nginx here

Only the L7 load balancers talk to this VM, so forgejo terminates the TLS connection itself with the certificate that os-bootstrap requests from the internal CA of the project — there is no nginx in front of it, and the unix socket setup of the on-premise host (group_vars/git_server) does not apply here.

In app.ini:

[server]
PROTOCOL  = https
HTTP_PORT = 3000
CERT_FILE = /etc/pki/certs/forgejo.s2i2s.cloud.isti.cnr.it.pem
KEY_FILE  = /etc/pki/keys/forgejo.s2i2s.cloud.isti.cnr.it-key.pem

Port 3000 keeps forgejo away from the privileged ports, so forgejo_bind_privileged_ports stays false.

Mind the permissions of the key. os-bootstrap installs it as root:root 0440, and forgejo runs as git: as it is, the service cannot read it. Either give the key a group that git belongs to, or set an ACL on /etc/pki/keys — the user_services_perms role of the playbooks already does this kind of thing for other services.

The load balancer verifies the certificate against the internal CA and its name (verify_host in the service definition), which the certificate satisfies because os-bootstrap puts the FQDN and every address of the VM among the SANs.

Git over SSH

No floating IP on this VM: the traffic goes through the load balancers.

client :22 -> Octavia TCP listener -> HAPROXY L7 :2222 -> forgejo :2222

The public port stays 22, so the clone URLs need no port. The port 22 of this VM belongs to sshd (that is how ansible gets in), so forgejo has to use its builtin SSH server on 2222 (forgejo_server_data.ssh_port): in app.ini, START_SSH_SERVER = true and SSH_LISTEN_PORT = 2222, with SSH_PORT = 22 advertised in the clone URLs. The app.ini file is not managed by the forgejo role.

The listener, its pool and its health monitor are in ../project-setup/octavia.tf; the ingress rule on the load balancers is in ../project-setup/haproxy.tf; the rule that lets the load balancers reach 2222 here is in this workspace.

Order of the applies

main_net_dns_router  ->  project-setup  ->  postgresql  ->  forgejo

This workspace reads the state of all three.

tofu init
tofu plan -out=forgejo.plan
tofu apply forgejo.plan

After the apply, regenerate the ansible inventory in infrastructure-playbooks, which reads this state:

ansible-playbook tofu-inventory.yml --diff

The playbook that configures the service is git-server.yml (role forgejo), which currently targets the git_server group: the generated inventory puts this VM in forgejo_cloud, under openstack_s2i2s.