Setting Up A Git Server On Ubuntu For Team Collaboration

A self-hosted Git server gives a small team control over its source code, access permissions, and project history without requiring every repository to live on a public platform. Ubuntu is a practical choice because it is well documented, receives regular security updates, and runs comfortably on a modest virtual machine or office server.

For a team in Australia, hosting location and connectivity deserve attention alongside Git commands. A server in a Sydney or Melbourne data centre may offer lower latency for local staff, while developers working from Perth, Brisbane, or regional areas will notice the quality of their NBN upload connection during large clones and pushes. A carefully configured SSH-based setup keeps daily collaboration simple while leaving room for stronger controls as the team grows.

Choose The Right Hosting Model

A Git server can run on a spare desktop, a dedicated machine, a virtual private server, or an internal cloud instance. A small office may choose a refurbished system with mirrored storage, while a distributed team might prefer an Ubuntu virtual machine in an Australian cloud region. A hosted server reduces hardware maintenance, but check its backup, breach notification, privacy, and data residency terms before uploading business or customer information.

For a straightforward installation, use a current Ubuntu LTS release such as Ubuntu 24.04 LTS. Give the host a stable private address on a local network, or assign it a fixed public address through your provider. A public server should have a domain name such as git.example.com, while an internal server can use a local DNS name. Avoid exposing Git services directly from a developer’s workstation, where sleep settings, changing IP addresses, and personal accounts create unnecessary risk.

Think about the team’s working pattern before choosing the design. A small group that needs private repositories can use bare Git repositories over SSH. A larger organisation may eventually need a web interface, pull requests, issue tracking, fine-grained permissions, and continuous integration through software such as Gitea, GitLab, or Forgejo. Starting with a simple SSH service is sensible when the main requirement is reliable version control.

Prepare The Ubuntu Host

Begin with a clean installation and update the operating system:

sudo apt update
sudo apt full-upgrade -y
sudo apt install git openssh-server ufw fail2ban -y

Set a meaningful hostname, confirm the server’s clock is correct, and create a separate administrator account rather than using root for routine work. Accurate time is important when reviewing logs, investigating failed logins, or matching events across an office network. Enable automatic security updates where appropriate, but test major operating system upgrades before applying them to a production Git host.

A developer’s Ubuntu workstation should also be kept current. If the machine needs Windows for business software, firmware tools, or a client application, follow a tested guide for dual-boot Ubuntu and Windows before using it for repository administration. Keep the server separate from desktop experimentation, and record its address, hostname, storage layout, and administrator contacts in a small internal document.

Configure the firewall conservatively:

sudo ufw default deny incoming
sudo ufw default allow outgoing
sudo ufw allow OpenSSH
sudo ufw enable
sudo ufw status verbose

If SSH runs on a non-standard port, change the rule to match it, but remember that moving the port is not a replacement for authentication controls. Before closing an existing session, open a second terminal and confirm that a new SSH login works.

Create A Restricted Git Account

A bare repository stores Git data without a checked-out working tree, making it suitable for a central remote. First create a dedicated system account and repository directory:

sudo adduser --system --group --shell /usr/bin/git-shell git
sudo install -d -o git -g git /srv/git
sudo -u git git init --bare /srv/git/team-app.git

The git-shell login prevents the account from opening a normal interactive shell. Developers can still use Git’s SSH transport, but a compromised Git key has fewer opportunities to run arbitrary commands. Give each person an individual account or SSH key rather than sharing a password or a single private key.

For a small team, administrators can place approved public keys in /home/git/.ssh/authorized_keys:

sudo install -d -m 700 -o git -g git /home/git/.ssh
sudo nano /home/git/.ssh/authorized_keys
sudo chown git:git /home/git/.ssh/authorized_keys
sudo chmod 600 /home/git/.ssh/authorized_keys

Each line should contain one developer’s public key, normally created with ssh-keygen -t ed25519 on their workstation. Never copy a private key to the server. When someone leaves the team, remove their public key promptly and review repository access rather than waiting for the next annual permissions check.

For better administration, use a central access tool or a Git platform once the key list becomes difficult to manage. A team member should be able to identify which key belongs to which person, and offboarding should take minutes rather than requiring a search through undocumented files.

Publish Repositories And Set Permissions

On a developer’s computer, add the new server as a remote:

git remote add origin git@git.example.com:/srv/git/team-app.git
git branch -M main
git push -u origin main

Other developers can clone it with:

git clone git@git.example.com:/srv/git/team-app.git

The path after the hostname must match the repository location on the server. A first connection will ask the user to verify the server’s host key. Teams should verify that fingerprint through a trusted channel, then accept it; blindly accepting a changed key can conceal a man-in-the-middle attack.

A bare repository does not automatically enforce a team policy. Add a README, a licence appropriate to the project, and a contribution guide describing branches, commit messages, reviews, and release tags. A common workflow is to keep main protected by convention, create short-lived feature branches, and merge changes after review. Git itself will accept direct pushes unless you add server-side hooks or use a platform with branch protection.

File permissions matter when several administrators manage repositories. The git account should own the bare repositories, while ordinary developers access them through SSH. Avoid making /srv/git world-writable. If a project contains secrets, remove them from the history with suitable Git tooling, rotate the exposed credentials, and store future secrets in environment variables or a secrets manager.

Secure SSH And Network Access

SSH keys are the foundation of a practical private Git service. On each client, developers can create an Ed25519 key with:

ssh-keygen -t ed25519 -C "developer@example.com"
ssh-copy-id git@git.example.com

If ssh-copy-id is unsuitable because the git account uses git-shell, an administrator can add the public key manually. Test the connection with ssh -T git@git.example.com; a message indicating that interactive shell access is unavailable is expected when git-shell is working correctly.

After every administrator has confirmed key-based login, consider disabling password authentication in /etc/ssh/sshd_config:

PasswordAuthentication no
PermitRootLogin no
PubkeyAuthentication yes

Validate the configuration and reload SSH:

sudo sshd -t
sudo systemctl reload ssh

Keep one existing administrative session open while testing a fresh connection. Use UFW to restrict SSH to an office IP or VPN range where practical. A public server should also use fail2ban, regular log review, and timely OpenSSH security updates. Teams operating under the Australian Privacy Act 1988 should assess whether repository contents include personal information and limit access, retention, and overseas exposure accordingly.

Australian businesses should document who controls the server and where backups are stored. A provider advertising an Australian region may still use overseas support systems or subprocessors, so read the contract rather than assuming “Sydney region” means every copy stays in Australia. For regulated work, involve the organisation’s privacy and security staff before choosing public hosting.

Establish A Reliable Team Workflow

Git is a collaboration system, not merely a file-sharing folder. Agree on branch naming, review expectations, and release procedures before several people begin editing the same code. For example, developers can push feature/short-description, open a review through the team’s chosen platform, and merge only after tests pass. Teams without a web interface can still review commits using git log, git diff, and protected server-side hooks.

Set repository identity on each workstation:

git config --global user.name "Alex Nguyen"
git config --global user.email "alex@example.com"
git config --global init.defaultBranch main

A .gitignore file should exclude build output, editor settings, local configuration, caches, and credentials. Add a lightweight test command to the team documentation, and use pre-commit hooks when they provide clear value. The goal is a repeatable process that works for a developer in Adelaide as well as someone working from a Melbourne office, not a collection of unwritten habits known only to the original administrator.

Time zones can affect release coordination. Australia spans several zones, and daylight saving applies in New South Wales, Victoria, Tasmania, South Australia, and the Australian Capital Territory but not Queensland, Western Australia, or the Northern Territory. Record scheduled maintenance and release times with an explicit zone or in UTC. This avoids confusion when a Sydney-based maintainer and a Brisbane-based developer interpret “Friday afternoon” differently.

For teams selling software in the Australian market, keep licence files, third-party notices, and deployment notes in version control. A repository history can help demonstrate who approved a change, but it is not a substitute for legal review, secure deployment, or a documented incident process.

Back Up, Monitor, And Maintain The Server

A Git repository contains valuable history, but one copy is not a backup. Back up /srv/git, SSH configuration, repository hooks, and relevant system documentation to a separate system. Use encrypted off-site storage when appropriate, and keep at least one backup disconnected or protected from accidental deletion. A backup that has never been restored is only an assumption, so test recovery by cloning a restored repository into a temporary directory.

A basic archive can be created with:

sudo tar -czf /var/backups/git-$(date +%F).tar.gz /srv/git

This is useful for a small installation, but it should not be the only scheduled method. Use a rotation policy so storage does not fill silently, monitor available disk space, and consider filesystem snapshots or a dedicated backup application for larger repositories. If the server uses an SSD, monitor its health and keep enough free space for repository maintenance.

Check SSH authentication logs and system service status regularly:

sudo journalctl -u ssh --since "24 hours ago"
sudo systemctl status fail2ban
df -h
sudo du -sh /srv/git/*

Run git fsck during planned maintenance to check repository object integrity, especially after an unexpected shutdown or storage warning. Keep Ubuntu, Git, OpenSSH, and fail2ban patched. Before an upgrade, take a tested backup and record the rollback plan.

When a project grows beyond a handful of users, move towards Gitea, Forgejo, or GitLab if the team needs browser-based reviews, account management, audit logs, webhooks, or CI runners. Deploying such a platform adds database, update, and backup responsibilities, so it should solve a real workflow problem rather than add complexity for its own sake.

A dependable Ubuntu Git server is built from a few disciplined choices: current software, individual SSH keys, restricted permissions, documented collaboration rules, tested backups, and a clear response when someone leaves the team. Start with one bare repository and a private network or VPN, then expand access only when the workflow and security controls are ready. For an Australian team, recording the hosting location, privacy obligations, time zone, and recovery procedure turns a working Git endpoint into a maintainable collaboration service.