git-gemini-forge 0.5.2

A simple Gemini server that serves a read-only view of public repositories from a Git forge.
# git-gemini-forge

A simple Gemini capsule (server) that bridges public repositories from a Git forge onto Geminispace. Inspired by masalachai's `gemini-git-browser`.

=> gemini://git.average.name Project Demo
=> https://geminiprotocol.net/ The Gemini protocol
=> https://github.com/masalachai/gemini-git-browser masalachai/gemini-git-browser

## Under Construction

> ⚠️ Warning
>
> This project is under active construction, and is missing basic features. Interface layouts, routes, and environment variables may change at any time until v1.0.0.

## Features

This capsule proxies a given git forge's public API, usually via localhost.

### Supported Forges

=> https://forgejo.org/ Forgejo
=> https://about.gitea.com/ Gitea
=> https://about.gitlab.com/ GitLab

### Forge support wishlist

=> https://man.sr.ht/ Sourcehut
=> https://github.com/ GitHub

### Routes

* `/` -> Lists several code repositories, sorted by recent activity.
* `/users` -> Lists several of the forge's users, but only if enabled. (See the "Environment Variables" section below.)
* `/users/{username}` -> Lists the given user's code repositories.
* `/users/{username}/{repository}` -> Lists the given repository's branches and code tree, along with a link to the HTTP view.
* `/users/{username}/{repository}/src/branch/{branch}` -> Not yet implemented.
* `/users/{username}/{repository}/src/branch/{branch}/{filename}` -> Not yet implemented.

### To do

* Present the first level of a repository's file tree.
* Present more repository metadata (description, etc.)
* Present a repository's arbitrary file tree.
* Render a repository's README file on its main page.
* Paginate long lists.
* Work out the kinks in GitLab integration.

## Installation

See below on configuring environment variables.

### Docker

Create a `compose.yaml` file like the following:

```yaml
services:
  git-gemini-forge:
    image: git.average.name/averagehelper/git-gemini-forge:latest
    container_name: git-gemini-forge
    restart: unless-stopped
    environment:
      - FORGE_TYPE=forgejo
      - FORGE_URL=http://localhost:3000
    volumes:
      - "./.certs:/app/.certs:ro"
    network_mode: "host"
```

See also the example `compose.yaml` file provided here.

=> compose.yaml

If your git forge is on a different network from the host, then omit `network_mode` and specify a `ports` map:

```yaml
services:
  git-gemini-forge:
    # [...]
    ports:
      - "1965:1965"
```

Then run:

```sh
docker compose pull
docker compose up -d
```

### Cargo

This crate is published on our own package registry. With `cargo` installed, run the following:

```sh
cargo install --index sparse+https://git.average.name/api/packages/AverageHelper/cargo/ git-gemini-forge
```

=> https://www.rust-lang.org/tools/install Install Cargo

Also available from crates.io:

```sh
cargo install git-gemini-forge
```

=> https://crates.io/crates/git-gemini-forge crates.io/git-gemini-forge

Then run with:

```sh
FORGE_URL=http://localhost:3000 git-gemini-forge
```

### Build from source

Clone this project using `git`. Then, with `cargo` installed, run the project using:

```sh
FORGE_URL=http://localhost:3000 cargo run --release
```

=> https://www.rust-lang.org/tools/install Install Cargo

## Environment Variables

- CERTS_DIR: The directory, relative to the current working directory when the binary runs, that `git-gemini-forge` should check for the `key.pem` and `cert.pem` files. See below on how to generate and configure those. Defaults to `.certs`.
- `FORGE_TYPE`: Describes the type of forge that is being proxied, and defines the expected shape of the API to call. Must be one of `forgejo`, `gitea`, or `gitlab`, case insensitively. Defaults to `forgejo`.
- `FORGE_URL`: The URL for the forge. The program will halt immediately if the given URL is malformed. Defaults to `http://localhost:3000` (a common port for running Forgejo).
- `FORGE_AUTH_TOKEN`: An optional token that would grant access to certain privileged routes, such as `/metadata` or `/users` on GitLab. If omitted, and proxying a forge that requires authorization, no authorization will be sent and some routes may respond with a Gemini `43 Proxy Error`.
- `FORGE_LIST_USERS`: Whether we should attempt to list users, for example at the `/users` endpoint. Consider leaving this disabled if your forge does not permit enumerating users. Defaults to `false`.

=> https://forgejo.org/docs/latest/admin/installation-docker/ Doc: Forgejo Installation with Docker
=> gemini://geminiprotocol.net/docs/protocol-specification.gmi Doc: Gemini Protocol Specification (see section Status 43---proxy error)

## Certificates

### For local development

Create TLS certificates like so:

```sh
mkdir -p .certs
cd .certs
openssl req -x509 -newkey rsa:4096 -keyout key.pem -out cert.pem -sha256 -days 1103760 -nodes -subj '/CN=localhost'
```

> ⚠️ Important
> Change the '/CN=localhost' part to your expected domain when using in production.

Note that the `-days` arg in the command above sets the cert to expire sometime around the year 3024. This is sufficient for use with Gemini capsules or local development, but not much else.

The `<project>/.certs` directory must contain `key.pem` and `cert.pem`, or the server will panic.

## Disclaimer

I am not responsible for misuse of this tool. The intent is for Forgejo admins to host this capsule alongside their own Forgejo installation, pinging the forge's API via localhost. While proxy via HTTPS is supported, proxying external git forges that you do not own is quite rude when done without permission. Be sure to obtain consent before bogging down someone else's server with proxy traffic.