{
    "product": "Cenvero Stratum",
    "generated_at": "2026-08-03T07:17:16+00:00",
    "format": "cenvero-docs-v1",
    "document_count": 1,
    "documents": [
        {
            "slug": "tenants",
            "title": "Tenants & Bandwidth",
            "category": null,
            "url": "https://stratum.cenvero.com/docs/tenants",
            "headings": [
                {
                    "level": 1,
                    "text": "Tenants & Bandwidth"
                },
                {
                    "level": 2,
                    "text": "What a tenant actually separates"
                },
                {
                    "level": 2,
                    "text": "Scoped API keys"
                },
                {
                    "level": 2,
                    "text": "The tenant quota"
                },
                {
                    "level": 2,
                    "text": "Your plan's speed ceiling"
                },
                {
                    "level": 2,
                    "text": "Bandwidth limits"
                },
                {
                    "level": 3,
                    "text": "Pools"
                },
                {
                    "level": 3,
                    "text": "What a limit does to traffic"
                },
                {
                    "level": 2,
                    "text": "Monthly usage quotas"
                },
                {
                    "level": 2,
                    "text": "See also"
                }
            ],
            "word_count": 1323,
            "markdown": "# Tenants & Bandwidth\n\nA **tenant** is a named owner you attach resources to — networks, addresses, API keys and a bandwidth allowance. If you run workloads for several customers, teams or environments on the same hardware, tenants are how you keep them apart and how you cap what each one can consume.\n\nIf everything on your nodes belongs to you, you can ignore tenants entirely. Nothing requires one.\n\n## What a tenant actually separates\n\nCreating a tenant does not create an enclosure that traffic cannot leave. It creates an **ownership label** plus two things that are genuinely enforced:\n\n| What you get | What it does |\n|---|---|\n| **Ownership of resources** | Networks and addresses are recorded against the tenant, so you can see and delete everything one customer owns as a unit. |\n| **A scoped API key** | A key that can act only for that tenant — it cannot read or change another tenant's resources. |\n| **A bandwidth cap** | A real rate limit, applied in the traffic path. See below. |\n\nIsolation *between* tenants comes from the network design — separate networks and firewall policy — not from the tenant record itself. Two tenants whose networks you have connected can reach each other; the tenant label does not stop that. Put each tenant on its own network and set your firewall default action to deny, and the separation is real. See [Zero-Trust Firewall](/docs/networking/firewall).\n\n```bash\nsudo cenvero-str-ctl tenant create --name acme\ncenvero-str-ctl tenant list\n```\n\nDeleting a tenant is a **cascade** — it removes that tenant's API keys, quota, networks and address allocations together:\n\n```bash\nsudo cenvero-str-ctl tenant delete <tenant-id>\n```\n\n## Scoped API keys\n\nA tenant key lets you hand out API access that is confined to one tenant, instead of sharing an operator key that can change everything.\n\n```bash\n# Mint a key (optionally labelled, optionally time-limited)\nsudo cenvero-str-ctl tenant key-generate <tenant-id> --name \"acme-portal\" --ttl 720h\n\ncenvero-str-ctl tenant key-list <tenant-id>\nsudo cenvero-str-ctl tenant key-revoke <key-id>\n```\n\nThe key is shown once, when it is minted. Give it a TTL if it is going into a system you do not fully control — a key that expires on its own is one less thing to remember to revoke.\n\n## The tenant quota\n\nA tenant's quota is its **bandwidth cap**, and that is the only resource capped. `0` means unlimited.\n\n```bash\nsudo cenvero-str-ctl tenant quota-set <tenant-id> --max-bandwidth-bps 1000000000\ncenvero-str-ctl tenant quota <tenant-id>\n```\n\nEverything else is deliberately **unlimited on every plan** — there is no cap on how many addresses, workloads, networks or firewall rules a tenant may have. If you need those bounded for commercial reasons, bound them in your own provisioning layer, where you can refuse the request and tell the customer why.\n\n## Your plan's speed ceiling\n\nAbove every limit you set yourself sits one you do not: **your licence carries the maximum speed the node may use**, and it is applied to the node's uplink.\n\n| Plan | Maximum speed per node |\n|---|---|\n| **Lab** (free, non-commercial) | 1 Gbps |\n| **Core** | 10 Gbps |\n| **Cloud** | 25 Gbps |\n| **Enterprise** | 100 Gbps |\n\n> These are the current plans. The [pricing section of the site](/#pricing) is the\n> authoritative list — your own ceiling is whatever your licence carries, which you\n> can read with `cenvero-str-ctl license status`.\n\nFour things worth knowing:\n\n- **It is per node, not per account.** Ten Core nodes are ten separate 10 Gbps ceilings, matching how the plans are priced.\n- **It is the node's total, shared across all its network cards.** A licensed node behaves as though its cards have exactly that much capacity between them: a 2 Gbps licence on a single 10 Gbps card passes 2 Gbps, and **two cards share the same 2 Gbps** — you can distribute traffic across them however you like, but the total is still 2 Gbps. Adding a card does not give you more headroom. (Your management interface is deliberately left alone — throttling the control plane would take the node out of its cluster.)\n- **Speeds are bits per second**, the way link speed and the plans are quoted — not bytes.\n- **It applies on top of anything you configure.** A tenant limit of 5 Gbps on a Core node gives that tenant 5 Gbps; setting a tenant to 50 Gbps does not lift the node past 10.\n- **Changing plan takes effect without a restart.** The node re-reads its licence periodically, so an upgrade raises the ceiling within about a minute of the new licence landing.\n\nGoing over the ceiling does not fail — it **throttles**. Traffic above the rate is held to it, exactly as described for bandwidth limits below, so a transfer slows rather than breaking.\n\nThe ceiling behaves like any other cap here — a credit allowance refilling at the licensed rate, with burst headroom so ordinary traffic is not penalised. See what that means for TCP and UDP below.\n\n## Bandwidth limits\n\nBandwidth is the one resource control that is real, and it is applied on the way **out** of a node — egress shaping. A limit is a rate in **bits per second**, and `0` always means unlimited.\n\nThere are two ways to apply one, and they answer different questions.\n\n**Per tenant** — \"this customer gets 1 Gbps in total\":\n\n```bash\nsudo cenvero-str-ctl tenant quota-set <tenant-id> --max-bandwidth-bps 1000000000\n```\n\n**Per target** — \"this particular workload gets 100 Mbps\", regardless of who owns it:\n\n```bash\ncenvero-str-ctl bandwidth list\nsudo cenvero-str-ctl bandwidth delete <id>\n```\n\nA per-target limit is submitted as a JSON object describing what to limit and at what rate — see the [API Reference](/docs/api) for the field names, and [CLI Reference](/docs/cli) for the command form.\n\n### Pools\n\nA **pool** is a shared allowance that several targets draw from together, rather than each holding its own independent cap. Use it when a group should be limited collectively — \"these five workloads share 500 Mbps between them\" — instead of five separate 100 Mbps limits that cannot lend capacity to one another.\n\n```bash\ncenvero-str-ctl bandwidth pool --help\n```\n\n### What a limit does to traffic\n\nThis is the part to understand before you set one, because the behaviour is not what \"shaping\" usually implies.\n\nA limit is a **credit allowance that refills at the rate you set**. Every packet spends credit equal to its size. While there is credit, traffic passes untouched. When the credit runs out, **traffic over the rate is dropped — not queued and delivered late.**\n\nThat distinction matters:\n\n- **TCP copes well.** Loss is exactly the signal TCP uses to slow down, so a TCP transfer finds the rate and settles there. This is the normal case and it works.\n- **UDP does not.** Nothing tells a UDP sender to slow down, so anything over the rate is simply lost. Video, voice, game traffic and metrics streams degrade rather than slow down. Size the limit for the peak these need, not the average.\n\nUnused credit accumulates up to a ceiling, so a burst after a quiet period passes at full speed and only sustained traffic is held to the rate. A short spike is not punished.\n\nTwo more consequences worth planning around:\n\n- **The cap is per node.** A tenant with workloads on three nodes has the limit applied on each of them — it is not a single allowance summed across the cluster.\n- **It applies on the way out.** Limiting what a workload can *receive* means limiting whoever is sending to it, which you only control if the sender is also yours.\n\n## Monthly usage quotas\n\nSeparately from rate limiting, a node can track **how much a workload transfers per calendar month** and act when it crosses a threshold. This is a volume cap, not a speed cap — the two are independent, and you can use either or both.\n\n```bash\ncenvero-str-ctl quota list\ncenvero-str-ctl quota get <mac>\n```\n\nCounters reset at the start of each month. Use rate limits to control how fast a tenant can go, and monthly quotas to control how much they can move in total.\n\n## See also\n\n- [Zero-Trust Firewall](/docs/networking/firewall) — the policy that actually separates tenants from each other.\n- [Networking Overview](/docs/networking/overview) — networks, endpoints, and how a workload joins one.\n- [Monitoring & Observability](/docs/monitoring) — reading real throughput per workload.\n- [API Reference](/docs/api) — tenant, quota and bandwidth endpoints.\n"
        }
    ]
}