Bots often send commands via `ssh user@host <command>` (exec request) rather than requesting an interactive shell. These were previously rejected silently. Now exec commands are captured, stored on the session record, and displayed in the web UI session detail page. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
108 lines
3.6 KiB
Markdown
108 lines
3.6 KiB
Markdown
# Oubliette
|
||
|
||
An SSH honeypot that logs login attempts, presents fake shells to "successful" logins, and tries to detect when a real human is poking around.
|
||
|
||
Named after the medieval dungeon - a place you throw people into and forget about them.
|
||
|
||
## Status
|
||
|
||
Early development. See `PLAN.md` for the roadmap.
|
||
|
||
## Usage
|
||
|
||
### Build
|
||
|
||
```sh
|
||
# With Nix
|
||
nix build
|
||
|
||
# With Go
|
||
nix develop -c go build ./cmd/oubliette
|
||
```
|
||
|
||
### Configure
|
||
|
||
Copy and edit the example config:
|
||
|
||
```sh
|
||
cp oubliette.toml.example oubliette.toml
|
||
```
|
||
|
||
Key settings:
|
||
- `ssh.listen_addr` — listen address (default `:2222`)
|
||
- `ssh.host_key_path` — Ed25519 host key, auto-generated if missing
|
||
- `auth.accept_after` — accept login after N failures per IP (default `10`)
|
||
- `auth.credential_ttl` — how long to remember accepted credentials (default `24h`)
|
||
- `auth.static_credentials` — always-accepted username/password pairs (optional `shell` field routes to a specific shell)
|
||
- Available shells: `bash` (fake Linux shell), `fridge` (Samsung Smart Fridge OS), `banking` (80s-style bank terminal TUI), `adventure` (Zork-style text adventure dungeon), `cisco` (Cisco IOS CLI with mode state machine and command abbreviation)
|
||
- `storage.db_path` — SQLite database path (default `oubliette.db`)
|
||
- `storage.retention_days` — auto-prune records older than N days (default `90`)
|
||
- `storage.retention_interval` — how often to run retention (default `1h`)
|
||
- `shell.hostname` — hostname shown in shell prompts (default `ubuntu-server`)
|
||
- `shell.banner` — banner displayed on connection
|
||
- `shell.fake_user` — override username in prompt; empty uses the authenticated user
|
||
- `web.enabled` — enable the web dashboard (default `false`)
|
||
- `web.listen_addr` — web dashboard listen address (default `:8080`)
|
||
- Session detail pages at `/sessions/{id}` include terminal replay via xterm.js
|
||
- `web.metrics_enabled` — expose Prometheus metrics at `/metrics` (default `true`)
|
||
- `web.metrics_token` — bearer token to protect `/metrics`; empty means no auth (default empty)
|
||
- `detection.enabled` — enable human detection scoring (default `false`)
|
||
- `detection.threshold` — score threshold (0.0–1.0) for flagging sessions (default `0.6`)
|
||
- `detection.update_interval` — how often to recompute scores (default `5s`)
|
||
- `notify.webhooks` — list of webhook endpoints for notifications (see example config)
|
||
|
||
### GeoIP
|
||
|
||
Country-level GeoIP lookups are embedded in the binary using the [DB-IP Lite](https://db-ip.com/db/lite.php) database (CC-BY-4.0). The dashboard shows country alongside IPs and includes a "Top Countries" table.
|
||
|
||
For local development, run `scripts/fetch-geoip.sh` to download the MMDB file. The Nix build fetches it automatically.
|
||
|
||
### Run
|
||
|
||
```sh
|
||
./oubliette -config oubliette.toml
|
||
```
|
||
|
||
Test with:
|
||
|
||
```sh
|
||
ssh -o StrictHostKeyChecking=no -p 2222 root@localhost
|
||
```
|
||
|
||
SSH exec commands (`ssh user@host <command>`) are also captured and stored on the session record.
|
||
|
||
|
||
### NixOS Module
|
||
|
||
Add the flake as an input and enable the service:
|
||
|
||
```nix
|
||
{
|
||
services.oubliette = {
|
||
enable = true;
|
||
package = inputs.oubliette.packages.${system}.default;
|
||
settings = {
|
||
ssh.listen_addr = ":2222";
|
||
auth.accept_after = 10;
|
||
auth.static_credentials = [
|
||
{ username = "root"; password = "toor"; }
|
||
];
|
||
};
|
||
};
|
||
}
|
||
```
|
||
|
||
Alternatively, use `configFile` to pass a pre-written TOML file instead of `settings`.
|
||
|
||
### Docker
|
||
|
||
Build a Docker image via nix:
|
||
|
||
```sh
|
||
nix build .#dockerImage
|
||
docker load < result
|
||
docker run -v /path/to/data:/data -p 2222:2222 -p 8080:8080 oubliette:0.8.0
|
||
```
|
||
|
||
Place your `oubliette.toml` in the data volume. The container exposes ports 2222 (SSH) and 8080 (web/metrics).
|