Skip to main content

Beebium Python Client

What is Beebium?

Beebium is a headless, cycle-accurate BBC Micro emulator with a client-server architecture. The emulator runs as a server process -- one per machine variant (Model B, B+, B+ 128K, B with ROM/RAM board) -- and is driven entirely over gRPC, so front-ends and automation talk to it across a well-defined protocol rather than being wired into the emulation core.

What is the Python client?

beebium is the Python client for that protocol: a typed API over the gRPC services for controlling and automating emulator instances from Python -- type on the keyboard, read the screen in any display mode, peek and poke memory, drive the debugger, mount discs, and more. It is built for pytest-based testing of BBC Micro software: a bbc fixture gives each test a fresh machine.

Relationship to beebium-server

beebium-server is a separate, optional package: platform wheels that carry the emulator itself -- the server binaries, the ROMs, the presets and the bundled extensions. Install both and you have a complete, self-contained headless system:

pip install beebium beebium-server

With beebium-server present, Beebium.launch() needs no arguments -- it finds the server and its ROMs in that wheel. Without it, the client works just as well with a server installed any other way (Homebrew, the .deb/.rpm packages, Scoop, or a checkout build) or one already running, reached with Beebium.connect().

Installation

With uv:

uv add beebium beebium-server        # add to your project
# or, into a plain virtualenv:
uv pip install beebium beebium-server

With pip:

pip install beebium beebium-server

beebium-server is optional (see above). On an externally-managed system install into a virtualenv (or use uv/pipx).

Extras

pip install beebium[imaging]     # + Pillow, for saving captured frames as images
pip install beebium[discovery]   # + zeroconf, for discovering servers over mDNS

Usage

Every example below is a real test that runs against the beebium-server wheel (see readme/snippets/), so the code here is the code that runs.

Launch a server

The flagship path: with beebium-server installed, launch() takes no arguments and stops the server again when the block exits.

from beebium.client import Beebium

# With the beebium-server package installed, launch() needs no arguments:
# the emulator binary and its ROMs come from that wheel, and the server is
# stopped again when the block exits.
with Beebium.launch() as bbc:
    bbc.expect("BASIC")            # wait for the boot banner / BASIC prompt
    bbc.keyboard.type("PRINT 2+2")
    bbc.keyboard.press_return()
    print(bbc.expect("4"))         # -> 4

Connect to a running server

from beebium.client import Beebium

# Connect to a server that is already running. The target defaults to
# localhost on port 48875 (0xBEEB); pass "host:port" to reach another.
with Beebium.connect() as bbc:
    bbc.debugger.stop()
    print(f"PC = 0x{bbc.cpu.pc:04X}")

Choose a variant or a specific server

from beebium.client import Beebium

# Pick a machine variant: "model-b" (default), "model-b-plus",
# "model-b-plus-128k" or "model-b-romram". To run a specific install
# instead of the default search, pass server="/path/to/beebium" (a binary
# or an install root), or set the BEEBIUM_SERVER environment variable.
with Beebium.launch(variant="model-b-plus") as bbc:
    bbc.expect("BASIC")

Type on the keyboard

Given a launched or connected bbc:

bbc.keyboard.type("PRINT 2+2")     # type text, shifting as needed
bbc.keyboard.press_return()

bbc.keyboard.key_down("A")         # or drive individual keys
bbc.keyboard.key_up("A")

Read the screen

bbc.video.screen_text() reads the displayed text in any mode. For MODE 7 (teletext) work, beebium.client.screen adds helpers -- read_mode7_screen, screen_contains, find, dump_screen -- that correct for hardware scrolling.

# Read the text the machine is displaying, whatever the screen mode.
text = bbc.video.screen_text().text

# Wait (up to a timeout) for text to appear -- pexpect-style automation.
bbc.expect("BASIC")

Read and write memory

# Side-effect-free peek -- safe even for I/O registers.
via_flags = bbc.memory.address.peek[0xFE4D]        # System VIA IFR
zero_page = bbc.memory.address.peek[0x0000:0x0100]

# Follow a 6502 vector (16-bit little-endian).
wrchv = bbc.memory.address.peek.word(0x020E)       # the OSWRCH vector

# Bus access reads and writes through the memory bus, like real hardware.
bbc.memory.address.bus[0x1900] = 0x42
value = bbc.memory.address.bus[0x1900]

Drive the debugger

state = bbc.debugger.stop()            # pause; returns the execution state
print(state.is_running)                # -> False
print(bbc.cpu.registers)               # A=.. X=.. Y=.. SP=.. PC=.. P=.. [flags]

# Break the next time the OS writes a character, then let it run. The
# breakpoint is removed automatically when the block exits.
with bbc.debugger.breakpoint(0xFFEE):  # OSWRCH entry point
    bbc.keyboard.type("X")             # the echoed key drives OSWRCH
    bbc.debugger.run_and_wait_for_stop()
    print(f"stopped at PC=0x{bbc.cpu.pc:04X}")

Testing with pytest

Installing beebium registers the pytest plugin, so the bbc fixture is available with no extra configuration:

# The beebium pytest plugin registers a `bbc` fixture: a fresh BBC Micro,
# launched and torn down per test. Install beebium and it is available with no
# conftest wiring.
def test_print(bbc):
    bbc.expect("BASIC")
    bbc.keyboard.type("PRINT 2+2")
    bbc.keyboard.press_return()
    assert bbc.expect("4") == "4"

Companion fixtures: bbc_shared (one machine per module), stopped_bbc (starts paused), and the session-scoped mos_filepath / basic_filepath. Point the plugin at a server or ROMs with --beebium-server / --beebium-rom-dir (or the BEEBIUM_SERVER / BEEBIUM_ROM_DIR environment variables).

Further reading

Fuller documentation and runnable programs live in the repository: see docs/ for the gRPC service reference and subsystem guides, and examples/ for end-to-end scripts. (Later: links to the published API reference.)

Contributing

Development happens in the Beebium repository. This README is generated -- do not edit README.md directly. See CONTRIBUTING.md for the checkout, uv and wheel-test workflow and for how to edit the README (its template and snippets).

License

GPL-3.0-or-later. See COPYING.txt.

Release files for beebium 0.1.14

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for beebium 0.1.14
File Size Uploaded
beebium-0.1.14.tar.gz 426.3 kB Details

Built distribution (wheel)

Table of built distributions (wheels) for beebium 0.1.14
File Interpreter ABI Platform
beebium-0.1.14-py3-none-any.whl Python 3 none any Details

Total release size: 828.5 kB

Release files / beebium-0.1.14.tar.gz

Download URL beebium-0.1.14.tar.gz
Size 426.3 kB
Tags Source
SHA-256 checksum
How to use checksums
0eb6c8d435e1e1f6c93d288de5dc257ce48dd6fc7e32d0db5adbbe7f89526a93
BLAKE2b-256 checksum
How to use checksums
2a0abc37105a3648e538a9c0621c6469316469f05abecd201d34dfffa7212e92
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via uv/0.12.3 {"installer":{"name":"uv","version":"0.12.3","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}

Release files / beebium-0.1.14-py3-none-any.whl

Download URL beebium-0.1.14-py3-none-any.whl
Size 402.2 kB
Tags Python 3
SHA-256 checksum
How to use checksums
0d207921a3cd49de1c4a8aa5a049b78159ae3f4aeeb6ec5e146b280fb54dc4c9
BLAKE2b-256 checksum
How to use checksums
cc18db58c738b5e3a88573893c2d57e696a3d5eda831babfec43cf4273ac80d4
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via uv/0.12.3 {"installer":{"name":"uv","version":"0.12.3","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}

Release history Release notifications | RSS feed

0.4.0

2 release files

0.3.0

2 release files

0.2.0

2 release files

0.1.17

2 release files

0.1.16

2 release files

0.1.15

2 release files

This release

0.1.14 This release

2 release files

0.1.13

2 release files

0.1.12

2 release files

0.1.11

2 release files

0.1.10

2 release files

0.1.9

2 release files

0.1.8

2 release files

0.1.7

2 release files

0.1.6

2 release files

0.1.5

2 release files

0.1.4

2 release files

0.1.3

2 release files

0.1.2

2 release 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