Skip to main content
Pre-release

This release is a pre-release and may not be stable for production use.

gbp-stack — Python bindings for the Group Protocol Stack

License: Apache 2.0

Python bindings for the Group Protocol Stack: a layered, end-to-end encrypted group-messaging protocol family built on top of MLS (RFC 9420).

This package wraps the native gbp_stack shared library through ctypes. The wheel for each supported platform bundles the appropriate native binary under gbp_stack/_native/<rid>/.

Layers

┌── application ──────────────────────────────────────────────────────┐
│   GtpClient · GapClient · GspClient   (TCP / UDP / SCTP-like)       │
├─────────────────────────────────────────────────────────────────────┤
│   GroupNode (GBP — IP-like base)                                    │
├─────────────────────────────────────────────────────────────────────┤
│   MlsContext (RFC 9420)                                             │
└─────────────────────────────────────────────────────────────────────┘

Payload codec

Each sub-protocol payload can be encoded as CBOR (default), Protobuf, or FlatBuffers. Pass PayloadCodec to send and accept; the chosen codec is surfaced in ev.codec on payload_received events.

from gbp_stack import GtpClient, PayloadCodec

frame = gtp_alice.send(alice, alice_mls, target=2, message_id=1,
                       text="hello", codec=PayloadCodec.FLATBUFFERS)
for ev in bob.on_wire(bob_mls, frame.wire):
    if ev.kind == "payload_received":
        codec = ev.codec or PayloadCodec.CBOR
        result = gtp_bob.accept(ev.plaintext, bob_mls.epoch, codec=codec)
        print(result.text)
Value Name Description
0 PayloadCodec.CBOR Default; pf field omitted from wire
1 PayloadCodec.PROTOBUF Protobuf via gbp-proto
2 PayloadCodec.FLATBUFFERS FlatBuffers via gbp-flat; lowest latency

Sub-protocol toolkits

Beyond the protocol clients, the package ships ready-made helpers:

  • MessageHistory + Watermark — bounded GTP message log + per-sender high-water mark for serving and consuming resync requests.
  • JitterBuffer — bounded GAP reorder window keyed by media_source_id, with push, pop_in_order, pop_force and late-frame detection.
  • RoleRegistry + Permissions — bind numeric role ids to permission bit-masks and check them with require / has.
  • CapabilitiesNegotiator — track per-member advertisements and query the intersection, union, group_supports and missing views.
  • SFrameSession + SFrameEncryptor — SFrame (draft-ietf-sframe-enc) E2EE for GAP audio frames; per-sender AES-GCM keys derived from MLS exporter, 1024-entry sliding-window replay protection.
  • encode_gbp_frame — low-level helper to construct a raw CBOR GBP frame.
  • lookup_error — return the CBOR ErrorObject for a known error code.

Coordinator events

NodeEvent surfaces three new event kinds for coordinator election:

kind Extra fields Meaning
coordinator_election_needed The local node should initiate GSP COORDINATOR_CLAIM
became_coordinator This node won the election
coordinator_claim claimant A peer sent COORDINATOR_CLAIM with this member id

Install

pip install gbp-stack==1.9.2rc2

Quick start

from gbp_stack import MlsContext, GroupNode, GtpClient

with MlsContext.create("alice") as alice_mls, \
     MlsContext.create("bob")   as bob_mls:

    bob_kp  = bob_mls.export_key_package()
    welcome = alice_mls.invite(bob_kp)       # alice auto-finalizes; epoch advances to 1
    bob_mls.accept_welcome(welcome)

    group_id = alice_mls.group_id
    with GroupNode.create(member_id=1, group_id=group_id) as alice, \
         GroupNode.create(member_id=2, group_id=group_id) as bob, \
         GtpClient.create() as gtp_alice, \
         GtpClient.create() as gtp_bob:

        alice.bootstrap_as_creator(alice_mls.epoch)
        bob.bootstrap_as_joiner(bob_mls.epoch)

        frame = gtp_alice.send(alice, alice_mls, target=2,
                                message_id=0xCAFE_F00D, text="hello")
        for ev in bob.on_wire(bob_mls, frame.wire):
            if ev.kind == "payload_received" and ev.stream_type == 2:  # StreamType.Text
                result = gtp_bob.accept(ev.plaintext, bob_mls.epoch)
                print(result.text)   # → "hello"
                # result.status is "new" (first message from this sender)
                # subsequent messages → "new"; duplicates → "duplicate"

GSP signals with per-signal arguments

Signals that target a specific member or resource require CBOR-encoded args. The send method accepts an optional args: bytes keyword argument.

import struct
from gbp_stack import GspClient, SignalType

# Minimal CBOR helpers
def cbor_uint(n: int) -> bytes:
    if n <= 23:     return bytes([n])
    if n <= 0xFF:   return bytes([0x18, n])
    if n <= 0xFFFF: return bytes([0x19, n >> 8, n & 0xFF])
    return bytes([0x1A, (n>>24)&0xFF, (n>>16)&0xFF, (n>>8)&0xFF, n&0xFF])

def cbor_map1(k: int, v: int) -> bytes:
    return bytes([0xA1]) + cbor_uint(k) + cbor_uint(v)

def cbor_map2(k0: int, v0: int, k1: int, v1: int) -> bytes:
    return bytes([0xA2]) + cbor_uint(k0) + cbor_uint(v0) + cbor_uint(k1) + cbor_uint(v1)

# Signal-specific args schemas:
#   MUTE / UNMUTE  → {0: target_member_id}
#   ROLE_CHANGE    → {0: target_member_id, 1: new_role_id}
#   STREAM_START / STREAM_STOP → {0: stream_type}
#   CODEC_UPDATE   → {0: codec_id}
#   JOIN / LEAVE   → no args required

with GspClient.create() as gsp_alice:
    # Mute member 3 (no role_claim needed for self-moderation)
    frame = gsp_alice.send(
        alice_node, alice_mls,
        target=0,  # 0 = broadcast
        signal=SignalType.MUTE,
        role_claim=0,
        request_id=1,
        args=cbor_map1(0, 3),  # {0: target_member_id=3}
    )

MLS multi-member group pattern

When inviting a member to an existing group (not the first invite), use invite_full so that existing members can process the commit:

# Alice adds Carol to an alice+bob group
commit, welcome = alice_mls.invite_full(carol_mls.export_key_package())
alice_mls.finalize_commit()          # alice's epoch advances
bob_mls.process_message(commit)      # bob stages the commit
bob_mls.finalize_commit()            # bob's epoch advances to match alice
carol_mls.accept_welcome(welcome)    # carol joins
assert alice_mls.epoch == bob_mls.epoch == carol_mls.epoch

Persisting MLS state

Serialise a context so it survives a restart, then restore it later — the restored context is at the same epoch and can send / receive again. The blob holds private key material, so store it encrypted at rest.

blob = mls.export_state()                   # persist (encrypted) to disk
# ... later / after restart ...
with MlsContext.restore_state(blob, "alice") as restored:
    assert restored.epoch == mls.epoch
    assert restored.group_id == mls.group_id

License

Licensed under Apache License, Version 2.0.

Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

gbp_stack-1.9.2rc2.tar.gz (27.9 kB view details)

Uploaded Source

Built Distributions

If you're not sure about the file name format, learn more about wheel file names.

gbp_stack-1.9.2rc2-cp311-cp311-win_arm64.whl (25.5 kB view details)

Uploaded CPython 3.11Windows ARM64

gbp_stack-1.9.2rc2-cp311-cp311-win_amd64.whl (1.4 MB view details)

Uploaded CPython 3.11Windows x86-64

gbp_stack-1.9.2rc2-cp311-cp311-manylinux2014_x86_64.whl (1.5 MB view details)

Uploaded CPython 3.11

gbp_stack-1.9.2rc2-cp311-cp311-manylinux2014_aarch64.whl (25.3 kB view details)

Uploaded CPython 3.11

gbp_stack-1.9.2rc2-cp311-cp311-macosx_11_0_x86_64.whl (1.4 MB view details)

Uploaded CPython 3.11macOS 11.0+ x86-64

gbp_stack-1.9.2rc2-cp311-cp311-macosx_11_0_arm64.whl (1.2 MB view details)

Uploaded CPython 3.11macOS 11.0+ ARM64

File details

Details for the file gbp_stack-1.9.2rc2.tar.gz.

File metadata

  • Download URL: gbp_stack-1.9.2rc2.tar.gz
  • Upload date:
  • Size: 27.9 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/7.0.0 CPython/3.13.14

File hashes

Hashes for gbp_stack-1.9.2rc2.tar.gz
Algorithm Hash digest
SHA256 c29d89f07a6787717db9107f1e1cfb71795075327237f9622e6310125fcbafb5
MD5 fbf9ea0cfab7810565f9c8aac08904ba
BLAKE2b-256 2f0315116031a5c6b05a51eecd80e9c4b308a8184c550b7ba40a5310fb93026d

See more details on using hashes here.

Provenance

The following attestation bundles were made for gbp_stack-1.9.2rc2.tar.gz:

Publisher: release.yml on F000NKKK/Group-Protocol-Stack

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file gbp_stack-1.9.2rc2-cp311-cp311-win_arm64.whl.

File metadata

File hashes

Hashes for gbp_stack-1.9.2rc2-cp311-cp311-win_arm64.whl
Algorithm Hash digest
SHA256 1126752586e1ff1fb435beb3c7b385aaa5b6fbd823be7d0d4c5b7ec4b0b28fbd
MD5 884e80ba523e032949640264403432d5
BLAKE2b-256 f301cca3ae4bd81334adffa327969de6b17e259db2c94e50ca5e5c56441453e4

See more details on using hashes here.

Provenance

The following attestation bundles were made for gbp_stack-1.9.2rc2-cp311-cp311-win_arm64.whl:

Publisher: release.yml on F000NKKK/Group-Protocol-Stack

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file gbp_stack-1.9.2rc2-cp311-cp311-win_amd64.whl.

File metadata

File hashes

Hashes for gbp_stack-1.9.2rc2-cp311-cp311-win_amd64.whl
Algorithm Hash digest
SHA256 9d309f7b1fcb2c1bb1d688daa76616bf9ba2d715b3dd639f2385fe3b85c722d7
MD5 20ca4ff2ca950547a53fe9389c398c49
BLAKE2b-256 3e4167908f7b0f1c6cd840b266c41db2cadca8c67da12cba8048f5994224133d

See more details on using hashes here.

Provenance

The following attestation bundles were made for gbp_stack-1.9.2rc2-cp311-cp311-win_amd64.whl:

Publisher: release.yml on F000NKKK/Group-Protocol-Stack

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file gbp_stack-1.9.2rc2-cp311-cp311-manylinux2014_x86_64.whl.

File metadata

File hashes

Hashes for gbp_stack-1.9.2rc2-cp311-cp311-manylinux2014_x86_64.whl
Algorithm Hash digest
SHA256 f0d49d7b00d0b2f952bf201f0f0d323808875f74973fc36571d2481f6a7036c1
MD5 34736d9c4bed9a87b83d13fb1e6872b8
BLAKE2b-256 34dc48efad8b061e84ea70a2076864d3b0c102258d64df564b3a88c799d69d98

See more details on using hashes here.

Provenance

The following attestation bundles were made for gbp_stack-1.9.2rc2-cp311-cp311-manylinux2014_x86_64.whl:

Publisher: release.yml on F000NKKK/Group-Protocol-Stack

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file gbp_stack-1.9.2rc2-cp311-cp311-manylinux2014_aarch64.whl.

File metadata

File hashes

Hashes for gbp_stack-1.9.2rc2-cp311-cp311-manylinux2014_aarch64.whl
Algorithm Hash digest
SHA256 bd2323dfa799162387f88dfac3cd215efef7756ea13fe5e4279698cd35b06f78
MD5 cdae15f1c515ce7daca16635ed2fe5c7
BLAKE2b-256 6e1f3bc52a8a92eb1aeb1072ba5c8f69b0e5c9574fe44c53cc659dbc0bd5d7b4

See more details on using hashes here.

Provenance

The following attestation bundles were made for gbp_stack-1.9.2rc2-cp311-cp311-manylinux2014_aarch64.whl:

Publisher: release.yml on F000NKKK/Group-Protocol-Stack

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file gbp_stack-1.9.2rc2-cp311-cp311-macosx_11_0_x86_64.whl.

File metadata

File hashes

Hashes for gbp_stack-1.9.2rc2-cp311-cp311-macosx_11_0_x86_64.whl
Algorithm Hash digest
SHA256 a7d15a3621e99bd734955d1f4f0810593feacfc7e489e5adc0af3e31a8e2ebe4
MD5 503511b8b543d741c3833977acca9f43
BLAKE2b-256 5c42bcfb04c1a47efb8d5d99ef4f0bc8e3b67f968592e22e2475f9055b9c06e9

See more details on using hashes here.

Provenance

The following attestation bundles were made for gbp_stack-1.9.2rc2-cp311-cp311-macosx_11_0_x86_64.whl:

Publisher: release.yml on F000NKKK/Group-Protocol-Stack

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file gbp_stack-1.9.2rc2-cp311-cp311-macosx_11_0_arm64.whl.

File metadata

File hashes

Hashes for gbp_stack-1.9.2rc2-cp311-cp311-macosx_11_0_arm64.whl
Algorithm Hash digest
SHA256 13fa787e5f1ca4fe9c45a1090b21816528c0357a56d22d58420edecc78e60957
MD5 f187b974dcc250006d5661300bbe5487
BLAKE2b-256 0b1899c8cd34d80a2ae00de8a2816f750825e68d25a9febee3c655800ccda17a

See more details on using hashes here.

Provenance

The following attestation bundles were made for gbp_stack-1.9.2rc2-cp311-cp311-macosx_11_0_arm64.whl:

Publisher: release.yml on F000NKKK/Group-Protocol-Stack

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Release history Release notifications | RSS feed

This release

1.9.2rc2 This release

7 files

1.9.1

7 files

1.9.0

7 files

1.8.2

7 files

1.8.1

7 files

1.8.0

7 files

1.7.0

7 files

1.6.0

7 files

1.5.5

7 files

1.5.4

7 files

1.5.3

7 files

1.5.2

7 files

1.5.1

7 files

1.5.0

7 files

1.4.2

7 files

1.4.1

7 files

1.4.0

7 files

1.3.0

7 files

1.2.3

7 files

1.2.2

7 files

1.2.1

7 files

1.2.0

7 files

1.1.4

7 files

1.1.3

7 files

1.1.2

7 files

1.1.1

7 files

1.1.0

7 files

1.0.1

7 files

1.0.0

7 files

0.2.0

7 files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page