Skip to content
githome

Smart HTTP

cloning, pushing, and authenticating over the Git Smart HTTP protocol

Githome implements the Git Smart HTTP protocol. Git clients negotiate capabilities and exchange pack data over four HTTP endpoints:

Endpoint Method Purpose
/{owner}/{repo}.git/info/refs?service=git-upload-pack GET advertise refs for clone/fetch
/{owner}/{repo}.git/git-upload-pack POST send pack data on clone/fetch
/{owner}/{repo}.git/info/refs?service=git-receive-pack GET advertise refs for push
/{owner}/{repo}.git/git-receive-pack POST receive pack data on push

Git discovers these automatically; you never call them directly.

Clone URL format

http://HOST/{owner}/{repo}.git
https://HOST/{owner}/{repo}.git

Both the .git suffix and its absence work. Example with a local server:

git clone http://localhost:3000/alice/myrepo.git

Authentication

All four transport endpoints require authentication for private repositories. Public repositories allow unauthenticated clone and fetch; push always requires a valid token.

URL credentials

Embed a personal access token directly in the URL:

git clone http://alice:TOKEN@localhost:3000/alice/myrepo.git

Git stores the URL, including the embedded credentials, in .git/config. This is convenient for scripts and CI environments where the token is already available as an environment variable:

git clone http://alice:${GITHOME_TOKEN}@localhost:3000/alice/myrepo.git

The store helper writes credentials to ~/.git-credentials in plain text. Use it when you want git to prompt once and remember the token:

git config --global credential.helper store
git clone http://localhost:3000/alice/myrepo.git
# git prompts for username and password; enter your token as the password

The osxkeychain helper on macOS stores credentials in the system keychain:

git config --global credential.helper osxkeychain

Set the credential helper per-host to avoid mixing up credentials on machines with multiple git hosts:

git config --global credential.https://git.example.com.helper store

.netrc file for automation

Create or append to ~/.netrc:

machine localhost login alice password TOKEN

For a custom hostname:

machine git.example.com login alice password TOKEN

Set permissions so only your user can read it:

chmod 600 ~/.netrc

Git reads .netrc automatically; no credential helper configuration is needed.

gh CLI integration

Authenticate the gh CLI against a self-hosted githome server:

gh auth login --hostname localhost:3000 --git-protocol http

gh prompts for a token and configures both the API client and the git credential helper for that hostname. After this, gh repo clone alice/myrepo and git push work without further credential setup.

To verify the auth state:

gh auth status --hostname localhost:3000

Configuring a remote after cloning

If you cloned without credentials and want to add them later:

git remote set-url origin http://alice:TOKEN@localhost:3000/alice/myrepo.git

Or leave the URL clean and rely on the credential helper:

git remote set-url origin http://localhost:3000/alice/myrepo.git
git config credential.helper store

Push configuration

Set push behavior to avoid ambiguous pushes:

git config push.default simple

With simple, git push pushes the current branch to its upstream tracking branch only, which is the safest default on servers that mirror GitHub behavior.

TLS termination

Githome does not terminate TLS itself. Run it behind a reverse proxy that handles certificates. Example Caddy configuration:

git.example.com {
    reverse_proxy localhost:3000
}

Example nginx block:

server {
    listen 443 ssl;
    server_name git.example.com;

    ssl_certificate     /etc/ssl/certs/git.example.com.crt;
    ssl_certificate_key /etc/ssl/keys/git.example.com.key;

    location / {
        proxy_pass http://127.0.0.1:3000;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        # Smart HTTP requires no request body size limit for push
        client_max_body_size 0;
    }
}

After setting up the proxy, use https:// URLs:

git clone https://alice:[email protected]/alice/myrepo.git

Blob download limit

GITHOME_SERVER_MAX_BLOB_BYTES (default 10 MiB) limits how many bytes the Contents API returns for a single blob via GET /repos/{owner}/{repo}/git/blobs/{sha}. This limit does not apply to git push or clone; pack data flows through the upload-pack and receive-pack endpoints without a size cap.

Git LFS

Git LFS is not supported. Attempting to push LFS pointer files will push the pointer text only; the LFS batch API (POST /objects/batch) is not implemented. Store large binary assets outside the repository or use an external LFS server.