Skip to main content

Python SDK for Brickly brick runtimes.

Project description

brickly-sdk-python

Python SDK for Brickly brick runtimes. It speaks BPP over stdin/stdout and keeps stdout reserved for protocol messages.

Quick Start

from brickly import BricklyRuntime

brick = BricklyRuntime("com.example.python")


@brick.on_command("hello")
def hello(ctx, input):
    ctx.progress(0.5, "working...")
    ctx.chunk("hello\n")
    return {"ok": True, "input": input}


brick.run()

The SDK handles:

  • host.hello -> runtime.ready
  • runtime.ping -> runtime.pong
  • command.invoke dispatch
  • command.cancel via ctx.cancel_event, ctx.is_cancelled(), and ctx.on_cancel(...)
  • command.progress, command.chunk, and command.output
  • host.* request id allocation and host.result / host.error routing
  • runtime.shutdown -> optional shutdown hook -> runtime.bye
  • ui.create_browser_window, WindowHandle.call(...), and event routing for window.*
  • events.publish(...) and events.on(...)
  • brick.platform.system.* / ctx.platform.system.*, plus brick.system.* / ctx.system.* aliases
  • brick.invoke(...) / ctx.invoke(...) for child cross-brick command calls inside command scope
  • brick.invoke_root(...) for root cross-brick command calls outside command scope
  • brick.invoke_stream(...) / ctx.invoke_stream(...) for streaming child cross-brick command calls
  • brick.open_session(...) / ctx.open_session(...) for stateful cross-brick sessions
  • brick.platform.clipboard.read_content() / set_content(...)

Logging

brick.log(...) writes plain messages to stderr. Stdout is reserved for BPP protocol messages. The Brickly host log center attaches the brick id, source, stream, and scope metadata when collecting stderr, so brick code should not add a [brickId] prefix by itself.

Window Example

from brickly import BricklyRuntime

brick = BricklyRuntime("com.example.window")


@brick.on_command("open")
def open_window(ctx, input):
    win = ctx.ui.create_browser_window("ui/index.html", {"width": 640, "height": 480})
    win.on("closed", lambda payload: brick.log("closed", payload))
    win.set_title("Hello from Python")
    return {"windowId": win.id}


brick.run()

Cross-Brick Invoke

Inside a command handler, use ctx.invoke to call another brick command. The SDK automatically sends the current parentRequestId, so the host attaches the child call to the same invocation graph. Brickly starts, reuses, and recycles the target brick instance automatically. Pass profile_id when the target brick should run with a specific Profile; omit it to use the target brick's default Profile.

result = ctx.invoke(
    "com.brickly.openai",
    "chat",
    {"prompt": "hello"},
    profile_id="work",
)

Use invoke_stream when the target command emits progress, chunks, or named outputs before its final result. The SDK sends host.invoke with stream: true and yields events in host order:

for event in ctx.invoke_stream("com.brickly.openai", "chat", {"prompt": "hello"}):
    if event["type"] == "progress":
        ctx.progress(event.get("progress", 0), event.get("message"))
    elif event["type"] == "chunk":
        ctx.chunk(event.get("chunk"))
    elif event["type"] == "output":
        ctx.output(event["name"], event.get("value"))
    elif event["type"] == "result":
        return event["result"]

If the host returns host.error, invoke_stream raises BppError, matching normal invoke error handling.

To create a top-level cross-brick call outside command scope, use the explicit root API:

result = brick.invoke_root(
    "com.brickly.openai",
    "chat",
    {"prompt": "hello"},
    profile_id="work",
)

The caller manifest must declare the target brick and allowed commands in dependencies:

"dependencies": {
  "com.brickly.openai": {
    "commands": ["chat"]
  }
}

Platform System API

brick.platform.system.*, brick.system.*, ctx.platform.system.*, and ctx.system.* call host system capabilities through BPP host.platform.system.*:

@brick.on_command("show-app-info")
def show_app_info(ctx, _input):
    return {
        "appName": ctx.system.get_app_name(),
        "appVersion": ctx.system.get_app_version(),
        "userData": ctx.system.get_path("userData"),
        "isMacOS": ctx.system.is_macos(),
    }

Current methods are show_notification, shell_open_path, shell_trash_item, shell_show_item_in_folder, shell_open_external, shell_beep, get_native_id, get_app_name, get_app_version, get_path, get_file_icon, read_current_folder_path, read_current_browser_url, is_dev, is_macos, is_windows, and is_linux.

get_path() supports home, appData, assets, userData, sessionData, temp, exe, module, desktop, documents, downloads, music, pictures, videos, recent, logs, and crashDumps. Runtime calls are still checked by manifest permissions on the host side: notifications require os.notification; Shell capabilities require os.exec; app info, paths, native ID, platform checks, and current folder path reads require os.env; file icons require fs.read. read_current_folder_path() works when Finder is frontmost on macOS or Explorer is frontmost on Windows; it raises CURRENT_FOLDER_UNAVAILABLE when no readable foreground file-manager folder is available. read_current_browser_url() is reserved and currently returns UNSUPPORTED_PLATFORM.

Platform Clipboard API

brick.platform.clipboard.* and ctx.platform.clipboard.* call host clipboard capabilities through BPP host.platform.clipboard.*:

@brick.on_command("replace-clipboard")
def replace_clipboard(ctx, _input):
    previous = ctx.platform.clipboard.read_content()
    updated = ctx.platform.clipboard.set_content({"kind": "text", "text": "Updated by Python"})
    return {"previous": previous, "updated": updated}

Current methods are read_content() and set_content(content).

Cross-Brick Sessions

Use ctx.open_session when the target brick keeps in-memory state that must survive across multiple command calls. Calls through the same session are routed to the same target brick instance, and each session.invoke automatically carries the current parentRequestId, until close() is called or the caller brick instance exits.

session = ctx.open_session("com.brickly.openai", profile_id="work")

try:
    session.invoke("start-thread", {"title": "Draft"})
    reply = session.invoke("chat", {"prompt": "continue the thread"})
finally:
    session.close()

profile_id is the target brick Profile ID. Session invokes are checked against the caller manifest's dependencies[target].commands on every command call.

Errors

Raise BppError to preserve a specific Brickly error code:

from brickly import BppError

raise BppError("INVALID_INPUT", "url is required")

Project details


Download files

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

Source Distribution

brickly_sdk-0.1.0.tar.gz (13.4 kB view details)

Uploaded Source

Built Distribution

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

brickly_sdk-0.1.0-py3-none-any.whl (13.3 kB view details)

Uploaded Python 3

File details

Details for the file brickly_sdk-0.1.0.tar.gz.

File metadata

  • Download URL: brickly_sdk-0.1.0.tar.gz
  • Upload date:
  • Size: 13.4 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.11.15

File hashes

Hashes for brickly_sdk-0.1.0.tar.gz
Algorithm Hash digest
SHA256 4f71e10ca1637b34e48a95be4672a636efde451aa8a66812a2022fb543bcd674
MD5 f5f75aea27d710c05cf5b0e7394395f6
BLAKE2b-256 46a935f97a700a7a79e7f43d03a57c53da271528a5dcd09e599a4398b0fa5d09

See more details on using hashes here.

File details

Details for the file brickly_sdk-0.1.0-py3-none-any.whl.

File metadata

  • Download URL: brickly_sdk-0.1.0-py3-none-any.whl
  • Upload date:
  • Size: 13.3 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.11.15

File hashes

Hashes for brickly_sdk-0.1.0-py3-none-any.whl
Algorithm Hash digest
SHA256 ebe10ed0883e5706cdbd7dc71c35e238513c2f90f86bd406f128d7e2bf4c7b68
MD5 8e0f8c2fcf6b661103fc5e6df4299e94
BLAKE2b-256 5a49992e0ca573dfeba8e5581dd7a2a7c99287420009856b03ed847d545d8bb1

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page