Self-hosted VM cloud platform

Hopper

A VM cloud platform for universities. It splits bare-metal machines into isolated containers that people can SSH into, with single sign-on, credit-based billing on a double-entry ledger, an event pipeline and network isolation between tenants.

Stack
  • Go
  • gRPC
  • FastAPI
  • Kubernetes
  • NATS JetStream
  • PostgreSQL
  • Keycloak
  • Cilium
  • SvelteKit

Fig. 1 · Hopper, component by component

Conceptual

Select a component, or trace a scenario.

Each box is a part of the system; arrows show how a request or event moves between them.

Conceptual. Drawn from the project description, not exported from a running cluster. Paths are simplified, and no scale, telemetry or benchmark is implied.
Component reference and scenarios as text
Web console
The SvelteKit front end people use to sign in, start containers and watch usage.
Keycloak
Single sign-on over OpenID Connect, with role-based access.
API gateway
The FastAPI gateway that fronts the platform’s API.
Orchestrator
A Go service, called over gRPC, that manages the lifecycle of Kubernetes pods.
Credit ledger
Credit-based billing on a double-entry PostgreSQL ledger. Advisory locks stop concurrent charges from racing each other.
Event pipeline
Carries platform events, including the one that shuts down an account’s workloads when its credits run out.
Live metrics
Real-time metrics, streamed to the browser over server-sent events.
Container · tenant A
An isolated, SSH-accessible container sliced out of bare-metal compute.
Container · tenant B
Another tenant’s container. Network policy keeps it apart from tenant A.
SSH client
People connect straight into their own container over SSH.

Sign in

  1. The console hands sign-in to Keycloak: single sign-on over OpenID Connect.
  2. Requests then reach the FastAPI gateway with the user’s identity and role attached.

Launch a container

  1. A launch request reaches the gateway.
  2. Credits are checked against the double-entry ledger under an advisory lock, so two requests can’t spend the same credit.
  3. The gateway calls the Go orchestrator over gRPC.
  4. The orchestrator creates the Kubernetes pod: an isolated container for this user.
  5. The user connects to it over SSH.

Credits run out

  1. An account’s credits are exhausted; an event goes onto the NATS JetStream pipeline.
  2. The orchestrator receives the event…
  3. …and terminates that account’s workloads automatically.

Live metrics

  1. Metrics from running containers are collected…
  2. …and streamed to the console in real time over server-sent events.

Tenant isolation

  1. Cilium zero-trust network policies sit between tenants: traffic from one tenant’s container to another’s is not allowed by default.

What it is

Hopper is a VM cloud platform for universities. It takes bare-metal compute and splits it into isolated containers that people can SSH into, so a university can give each student or researcher their own machine on hardware it already owns.

What I built

  • Orchestration. A Go service, called over gRPC, manages the lifecycle of the Kubernetes pods that people SSH into.
  • Gateway. A FastAPI gateway sits in front of the platform’s API.
  • Identity. Keycloak handles OIDC single sign-on with role-based access.
  • Billing. Usage is charged in credits on a double-entry PostgreSQL ledger. Two charges against the same account can race each other, so ledger writes take PostgreSQL advisory locks.
  • Events. A NATS JetStream pipeline carries platform events. When an account runs out of credits, its workloads are shut down automatically.
  • Live metrics. Metrics stream to the browser in real time over server-sent events.
  • Isolation. Cilium zero-trust network policies keep tenants’ containers apart.

Why a double-entry ledger

A single balance column that goes up and down is easy to write and hard to audit. A double-entry ledger records every credit movement as a pair of entries, so the balance can always be recomputed and checked against the history. The advisory locks stop two concurrent charges from spending the same credit twice.

Reading the diagram

The diagram above is drawn from the project description. It isn’t exported from a running cluster. Pick a scenario to follow a request through the system, or click a component to see what it does.

Site index