Host Your Own Private GitHub with

Mar 24, 2016

GitHub is an amazing platform. It has completely revolutionized the way developers work together on software and has inspired countless individuals and organizations to open-source their code for a more transparent, collaborative development world. It encourages developers to work according to best practices and renowned coding styles, making it easier for people to work together on projects, and boosting overall developer proficiency.

I adore GitHub. Every time I start working on a personal project in my own free time, I can't wait for the exciting moment when I finally share it with the world by typing git push origin master, hoping that someone stumbles upon it someday. That's usually not the case though, as most of my projects go unnoticed due to the vast number of GitHub repositories. But hopefully, when someone Googles a specific need that I have managed to answer with one of my projects, they'll be able to find it and complain about something not working as it should. =)

Private Repositories

What about projects that you are not yet ready to share with the world? Maybe your code isn't perfect yet, or maybe it contains sensitive database credentials or secret API keys that you definitely don't want out there in the open? Maybe you're behind a corporate firewall and can't host your code on cloud services like GitHub? Or maybe you think you built a project that won't benefit anyone else, ever? Maybe, just maybe, you don't want to host your sensitive private repositories on a shared cloud with other people's code, having it sit there, waiting until someone finds a way in, as this talented gentleman did?

GitHub's private repository plan for individuals starts at $7/month. I think that's a bit expensive -- people working on their personal pet projects should be able to create a few private repositories for free. A $7/month fee can get expensive if you plan to have your projects hosted privately on GitHub for years to come. And this doesn't change the fact that your code is sitting in a shared cloud, targeted by many skilled individuals.


How about hosting the repositories on your own servers? There are several host-it-yourself git services, but some of them are extremely complicated to set up, requiring you to sift through slow and complicated installation steps that don't always go as planned, others are quite ugly, and some are simply limited. Luckily, I found Gogs, and it is the easiest of them all to setup and feature-rich, delivering the closest experience to GitHub than any other self-hosted git service!

Meet Gogs

Gogs lets you host your own private GitHub on your own servers. Literally. It's a very detailed clone of GitHub, both in design and features. It's built in Go and works really, really fast! Check out the live demo here. The fact that it's a GitHub clone makes it really easy to use if you're already used to GitHub's clean interface.


Let's go ahead and set up Gogs on a freshly-spun Ubuntu 14.04 EC2 instance on Amazon Web Services! You can also perform these steps on any other cloud provider, if you're not into AWS for some weird reason that is beyond me.

Launch an Instance

Let's spin-up a new EC2 instance by heading over to the EC2 launch wizard on AWS. Make sure to select Ubuntu Server 14.04 LTS (HVM), as the following installation guide is tailored to debian-based distros, specifically Ubuntu.

Ubuntu Server

If you intend to be the only one accessing Gogs, Amazon's new t2.nano instance class will definitely suffice. I'd recommend assigning an Elastic IP to your instance and exposing ports 22 (preferably only to your IP) and an additional port that Gogs will listen on, port number 1337, because we're cool. =)

If you happen to own a domain name, I'd highly recommend creating an A Record at your DNS provider and pointing it at the EC2 server's Elastic IP so that you'll be able to access Gogs via a human-friendly URL, e.g. This is a requirement if you wish to use Gogs over HTTPS.

A Record

Go ahead and grab a cup of coffee while your instance is spinning up.


Install Dependencies

SSH into the instance and run the following command to update your repository cache and install some basic dependencies for Gogs:

sudo apt-get update
sudo apt-get install -y wget unzip git

Let's go ahead and create a new user called git that will run Gogs and have full ownership over its files:

sudo useradd --system --create-home git

This will create a system user for Gogs and a home directory in /home/git.

Switch the shell over to the git user and head over to its home directory:

sudo su git
cd ~
Download Gogs

Grab the latest Gogs version as a .zip archive from here -- you'll probably need the amd64 archive since your instance is 64-bit (check with uname -a, look for x86_64).

At the time of writing, the latest version is v0.9.13. Let's grab it by using wget:

unzip gogs*.zip
rm -rf gogs*.zip

This will download and unzip Gogs for you into the /home/git/gogs folder.

Run the Binary

Gogs is extremely easy to run -- the archive includes a binary called gogs that you can invoke directly to run the service, specifying the port as an argument:

cd gogs
./gogs web --port=1337

Look for the Listen: log message to verify that everything is working as expected. If so, go ahead and browse to the hostname pointing to your EC2 server, e.g.

You should be able to see the following installation screen:

Install Screen

If not, you try accessing your server via its Elastic IP, e.g., and if that still doesn't work, you most likely didn't configure your EC2 security group correctly. Make sure any IP address can access port 1337 in the EC2 server's security group.

Configure Gogs

Make sure to select SQLite3 as the database type, as it requires no configuration at all. The rest of the configuration is up to you, go crazy!


Be sure to update the Domain and Application URL in the Application General Settings section to point to your subdomain or Elastic IP address. Be sure to use https:// as the protocol if you wish to set up HTTPS to access Gogs.

This one's important: Make sure to tick Disable Self-registration and Enable Require Sign In to View Pages in the Optional Settings section so Gogs operates in private mode.


Also, set up an account for yourself under Admin Account Settings.

Go ahead and click Install Gogs when you're done. You'll now be presented with a friendly message and a sign-in screen.

Install Success

After signing in, you'll be able to create repositories, clone, push, and whatever else your heart desires.

That's all, folks!

Gogs Home Page

Just kidding! What about HTTPS encryption? How about setting up a daemon to make sure it runs forever, even if the server reboots? Let's get to it!

Set Up the Gogs Daemon

Gogs provides a daemon script that we can use to have the system automatically run Gogs for us when it boots.

Kill the running Gogs instance, log out of the git user's shell and back into ubuntu, and then run the following commands to download the Gogs init.d script and make it executable:

cd /etc/init.d 
sudo wget
sudo chmod +x gogs

Now all we need to do is edit the init script to add our port to the gogs binary argument string. Using sed we can automatically find and replace within the gogs daemon file without opening it, using the following command:

sudo sed -i -e 's/DAEMON_ARGS="web"/DAEMON_ARGS="web --port 1337"/g' gogs

Let's try running the service now:

sudo service gogs start

If all is well, you should be able to browse to your Gogs instance at

Let's configure Ubuntu to start Gogs automatically after booting:

sudo update-rc.d gogs defaults
sudo update-rc.d gogs enable

You can make sure this actually works by rebooting the system:

sudo reboot

Gogs should be accessible automatically after reboot completes.

HTTPS Encryption

I'd strongly advise against using Gogs without HTTPS encryption, as your credentials will then be exposed to eavesdroppers using a very simple man-in-the-middle attack whenever you connect via a public Wi-Fi hotspot.

Luckily, setting up HTTPS is dead-simple and free, thanks to Amazon's new AWS Certificate Manager. All you need is a domain name!

Request an ACM Certificate

Follow this tutorial I posted a month ago to generate a wildcard ACM certificate for your domain. Once that's done, all that's left is to set up an Elastic Load Balancer to handle the HTTPS connection on behalf of Gogs.


Set Up an Elastic Load Balancer

Head over to the ELB creation wizard. Specify a name for your Elastic Load Balancer and set the following port forwarding configuration to forward incoming HTTPS traffic at port 1337 to your instance's port 1337 as HTTP traffic:

ELB Configuration

Create a new security group for your ELB, specifying the following rule to allow anyone to access port 1337 on your ELB:

ELB Security

Finally, choose your generated ACM certificate by selecting Choose an existing certificate from AWS Certificate Manager (ACM):

ACM Certificate

You can leave the Predefined Security Policy intact -- AWS already selected the most up-to-date policy available.

For the ELB's health check, configure it to ping the /user/login path, which always returns 200 OK if Gogs is currently running:

Health Check

Finally, select your EC2 instance and create the ELB!

Point Your Subdomain to the ELB

Now, all that's left is to modify your DNS configuration, changing the A Record you created before to a CNAME record, setting the value to your Load Balancer's DNS Name, which you can retrieve by going to the Load Balancers page.

DNS Name

Once the DNS change propagates through the Internet, you'll be able to access Gogs securely through encrypted HTTPS via the same hostname and port:

That's it!

I'm serious this time. You've successfully set up a persistent, self-hosted, secure, and private Git service! Now get back to working on your personal projects!