Koppel je Go-code niet aan GitHub

Een van de goede functies van Go is dat je je code namespace't met de locatie waar de code kan worden opgehaald. Dit betekent dat als je je Go-code host op http://github.com/thetrueares/boneclone, je de regel import “github.com/thetrueares/boneclone” gebruikt en Go deze via git ophaalt. Dit maakt het zeer eenvoudig om te weten waar je bugs moet melden voor open source-bibliotheken en maakt het ophalen en distribueren van Go-bibliotheken erg makkelijk zonder een centraal pakketbeheersysteem. Voor velen is dit simpelweg de locatie van de git-hosting, maar dit heeft nadelen. Je zou je eigen aangepaste domein moeten gebruiken, en ik zal uitleggen waarom.

Het probleem

Het belangrijkste probleem met het gebruik van je git-hostinglocatie is dat je code nu gekoppeld is aan een hostingprovider. Dat wil zeggen: als je je git-hosting verplaatst naar GitLab, moet je je code wijzigen! Anders haal je de oude versie op. Dit kan ertoe leiden dat je geen hostingprovider kunt wijzigen vanwege de hoeveelheid overhead die gepaard gaat met het overstappen. Je eindigt dus letterlijk met code die gekoppeld is aan GitHub. Dat klinkt volkomen krankzinnig, maar het is iets wat in de Go-community vrijwel de facto standaard is.

Ik heb gezien dat dit probleem een enorm issue werd voor een bedrijf dat tegelijkertijd GitLab, GitHub en Azure Devops gebruikte. Omdat het wijzigen van de locatie van de code zo'n grote taak voor hen was en ze geen "tijd hadden", was het voor hen makkelijker om op drie platforms tegelijk te werken. Dit is waarom ik Boneclone heb gebouwd om skeleton-code replicatie over meerdere git-hostingplatforms tegelijkertijd te beheren. Dit probleem kostte het bedrijf dus letterlijk geld, aangezien ze tegelijkertijd voor drie hostingdiensten moesten betalen.

De oplossing

De oplossing is om aangepaste domeinen te gebruiken zoals go.iain.rocks, go.uber.org, go.mongodb.org, etc. Hiermee kun je simpelweg wijzigen waar die domeinen naartoe wijzen. Bijvoorbeeld: go.iain.rocks/boneclone wijst naar github.com/thetrueares/boneclone, en als ik overstap naar GitLab verandert er voor de eindgebruikers niets; het installatiecommando blijft hetzelfde.

Naar mijn mening zou elk commercieel softwareontwikkelteam dat Go gebruikt, aangepaste domeinen moeten gebruiken voor het namespacen van hun interne bibliotheken en pakketten. Het is een eenvoudige manier om elke zinloze koppeling te voorkomen.

Hier is een kopie van mijn configuraties, zodat je dit ook voor jouw projecten kunt instellen.

Nginx.conf

server {
    server_name go.iain.rocks;
    root /var/www/go.iain.rocks;
    index index.html;

    location / {
        # Check if the query string does NOT contain 'go-get=1'.
        # The '~' is for a case-sensitive match.
        if ($args !~ go-get=1) {
            # This is a human visitor. Issue a permanent redirect to GitHub.
            # $request_uri will be the path, e.g., /boneclone
            return 301 https://github.com/that-guy-iain$request_uri;
        }
        # If it's the Go tool (with ?go-get=1), serve the HTML file as before.
        try_files $uri $uri/ =404;
    }

    # --- Your SSL configuration from Certbot should remain here ---
    listen 443 ssl;
    listen [::]:443 ssl;
    ssl_certificate /etc/letsencrypt/live/go.iain.rocks/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/go.iain.rocks/privkey.pem;
    include /etc/letsencrypt/options-ssl-nginx.conf;
    ssl_dhparam /etc/letsencrypt/ssl-dhparams.pem;
}

# The HTTP to HTTPS redirect block should also remain.
server {
    listen 80;
    listen [::]:80;
    server_name go.iain.rocks;
    return 301 https://$host$request_uri;
}

index.html

<!DOCTYPE html>
<html>
<head>
    <meta charset="utf-8">
    <meta name="go-import" content="go.iain.rocks/boneclone git https://github.com/that-guy-iain/boneclone">
    <meta name="go-source" content="go.iain.rocks/boneclone https://github.com/that-guy-iain/boneclone https://github.com/that-guy-iain/boneclone/tree/master{/dir} https://github.com/that-guy-iain/boneclone/blob/master{/dir}/{file}#L{line}">
</head>
<body>
</body>
</html>