tbot’s configuration is also done in python. There are two parts that can be configured: The lab and the board. If no lab is configured, tbot creates a LocalLabHost. If no board is configured, testcases trying to access it simply fail.

Lab Config

The lab config can be chosen with the -l commandline parameter. It should be a python module with a global LAB that is a class derived from LabHost. It might look like this:

import getpass
import tbot
from tbot.machine.linux import lab
from tbot.machine import linux

class PolluxLab(lab.SSHLabHost):
    name = "pollux"
    hostname = ""
    username = getpass.getuser()

    def workdir(self) -> "linux.Path[PolluxLab]":
        return linux.Workdir.static(self, f"/work/{self.username}/tbot-workdir")

LAB = PolluxLab

For the list of possible parameters, take a look at the LocalLabHost and SSHLabHost classes.

Board Config

The board config can be chosen with the -b commandline parameter. It should be a python module with at least a global BOARD that is a class derived from Board. If applicable, it can also export the UBOOT global which should be a class derived from UBootMachine and LINUX which should be derived from LinuxMachine. If both UBOOT and LINUX are exported, LINUX should be a LinuxWithUBootMachine. But this is not enforced.

An example board config might look like this:

from tbot.machine import board
from tbot.machine import linux

class BeagleBoneBlack(board.Board):
    name = "bbb"
    connect_wait = 3.0

    def poweron(self) -> None:
        self.lh.exec0("remote_power",, "on")

    def poweroff(self) -> None:
        self.lh.exec0("remote_power",, "off")

    def connect(self) -> channel.Channel:
        return self.lh.new_channel("connect",

class BeagleBoneUBoot(board.UBootMachine[BeagleBoneBlack]):
    prompt = "=> "

class BeagleBoneLinux(board.LinuxWithUBootMachine[BeagleBoneBlack]):
    uboot = BeagleBoneUBoot
    username = "root"
    password = None
    shell =  # Setting the right shell is very important!
    boot_commands = [
        ["setenv", "serverip", ""],
        ["setenv", "netmask", ""],
        ["setenv", "ipaddr", ""],
        ["mw", "0x81000000", "0", "0x4000"],
        ["tftp", "0x81000000", "bbb/tbot/env.txt"],
        ["env", "import", "-t", "0x81000000"],
        ["setenv", "rootpath", "/opt/..."],
        ["run", "netnfsboot"],

BOARD = BeagleBoneBlack
UBOOT = BeagleBoneUBoot
LINUX = BeagleBoneLinux

For info on the possible configuration options, checkout the docs for Board, UBootMachine, LinuxWithUBootMachine, and LinuxStandaloneMachine.


Sometimes your config needs some flexibility. To keep you from having to edit the config file every time, tbot has a feature called flags. Flags can be specified on the commandline using -f flagname and you can check if they are set in your config like this:

if "flagname" in tbot.flags:
    tbot.log.message("Flag ist set!")
    tbot.log.message("Flag ist NOT set!")

To make flags easily discoverable, you should add all available flags to a global named FLAGS:

    "flagname": "Short description of this flag",

You can then list all available flags using tbot --list-flags.