No description
  • Go 94.4%
  • Shell 4.6%
  • Makefile 1%
Find a file
langonnet 3f09c03506 feat: Export flag + minors-adjustements-3 (#6)
Ajout d'une subcommand export qui permet d'exporter les informations du serveur Vpigo provenant de la db et de la config sous la forme d'une config Wireguard. Une option --output est disponible pour choisir d'avoir l'export dans un fichier au lieu du stdout.
Correctifs et changements mineurs.

Reviewed-on: #6
Reviewed-by: Valentin Doreau <v.doreau@e-durable.ch>
2026-05-07 14:35:16 +02:00
.forgejo/workflows feat(build): add makefile and ci 2026-04-02 15:18:48 +02:00
cmd feat: Export flag + minors-adjustements-3 (#6) 2026-05-07 14:35:16 +02:00
deb test(build): point to RecycledCloud instead of langonne 2026-04-17 13:11:09 +02:00
doc doc: update 2026-04-08 16:49:28 +02:00
posting refactor(type): Set correct request type 2026-04-02 14:32:57 +02:00
.gitignore chore(gitignore): add vpigo 2026-04-02 10:18:30 +02:00
go.mod feat: Wireguard + minors-adjustements (#4) 2026-05-01 22:14:06 +02:00
go.sum feat: Wireguard + minors-adjustements (#4) 2026-05-01 22:14:06 +02:00
main.go feat: Export flag + minors-adjustements-3 (#6) 2026-05-07 14:35:16 +02:00
Makefile feat(build): add makefile and ci 2026-04-02 15:18:48 +02:00
README.md feat: Export flag + minors-adjustements-3 (#6) 2026-05-07 14:35:16 +02:00

Vpigo

Vpigo is an API written in Go(1.26.1) that expose some endpoints that allow manage Wireguard peers on the server. Peers information are keep in a SQLite database, client private key is stored but encrypt with AES-256-GCM.

Vpigo needs Wireguard installed and must be run as root to manipulate Wireguard interface.

Endpoints

endpoint type HTTP Code result note
/create/{vpn_id} POST 201,400,409,500 wg config Return the client configuration in plaintext format
/delete/{vpn_id} DELETE 204,400,404,500 none
/enable/{vpn_id} PATCH 204,400,404,500 none
/disable/{vpn_id} PATCH 204,400,404,500 none
/config/{vpn_id} GET 200,400,404,500 wg config Return the client configuration in plaintext format

API Configuration

The configuration file is located at /etc/vpigo/vpigo.json. All keys are required.

key type description
aes_256_secret_key base64 A 32 bytes encoded base64 string to encode the Wireguard client private key in the database.
auth_token str Token that will be used to authenticate with the API.
database_path filepath (Optional) Path to the SQLite database file. Default at /var/lib/vpigo/clients.db
endpoint fqdn|ip Endpoint that peers will use to connect to the Wireguard server.
listening_addr hostname _port Address that the API will listen on.
log_level str Define log level, case insensitive. Debug|Info|Warn|Error
network_ipv6 cidrv6 Network that the API will use to generate server and peers IPs.
server_public_key base64 Wireguard server public key.
wireguard_port port Port that the Wireguard server will listen on.

For more details on the type used refer to the Go validator package documentation

Key Rotation

To make a rotation of the AES key, you need to stop the program, then execute the following command :
vpigo --rotate-aes-key "New32BytesKey"
If no error occurs, replace the old key in the configuration file by the new one and start the program.

Example

Example of configuration file :

{
	"log_level":"debug",
	"auth_token" : "supertoken",
	"aes_256_secret_key":"QkJCQkxDTnEzUEFENlZzWFlMPVlGQWFDaVlxbEhxSUE=",
	"listening_addr":":8080",
	"network_ipv6":"2a0d:d9c4:c4:d::/96",
	"endpoint":"vpn.swdn.ch.recycled.cloud",
	"wireguard_port":51820,
	"server_public_key_path": "/etc/wireguard/public_key",
	"database_path":"db.db"
}

Technical Choices

CLI

I chose not to use a third-party package because it was not worth it for the current usage, the standard flag package is enough on its own. The downside is that I have to write the output of --help by myself.

Configuration

For the file format, I chose json because it is well integrated in Go. I just have to write flags to the configuration structure and I can map to it with a few lines of code.

To easily check fields that are loaded from the json file, I use Validator. It allows me to write validation flags in the configuration structure that avoid to manually verifying each field and there are a lots of custom types like: filepath,cidrv6 or hostname_port.

ORM

I chose to use an ORM because it allows me to easily manipulate the database using Go structs. This helps me minimize my interaction with raw SQL and results in more readable code. The ORM I chose is GORM because it is mature, widely used, and well-documented. It also has Prometheus metrics that can be useful to us.

Important: because I use GORM SQLite driver, which use CGO enabled package, you are required to have a gcc compiler present within your path.

WireGuard

To generate WireGuard private key, the easiest way is to use the Go implementation of WireGuard. Then Vpigo stores encrypted peers private key in the database. More details in cmd/wg/wireguard.go for the private key generation and in cmd/db/aes.go for the private key encryption in SQLite.

Private Key Encryption

The algorithm used to encrypt keys is AES-GCM 256 because it is the first one that came to my mind. It's not the most modern, but it remains efficient and quantum proof.

Error Handling

The philosophy of Go encourages errors to be returned as a value, which is very verbose. Vpigo error management is then based on a Panic-based Error Handling. Since Vpigo is primarily a web server and each request is a goroutine, an error middleware has been implemented that incorporates recover(), as well as an error structure AppError and a function Check(). All this allows us to use panic() in the functions called by the handlers, ensuring that a proper HTTP error is returned and avoiding the need to escalate errors through the functions.

Architecture

API Design