# libtmux

> Typed library that provides an ORM wrapper for tmux, a terminal multiplexer.

- **URL**: https://www.freshcrate.ai/projects/libtmux
- **Author**: pypi
- **Category**: Frameworks
- **Latest version**: `v0.58.0` (2026-05-23)
- **License**: MIT
- **Source**: https://github.com/tmux-python/libtmux/issues
- **Homepage**: https://pypi.org/project/libtmux/
- **Language**: Python
- **GitHub**: 1,163 stars, 117 forks
- **Registry**: pypi (`libtmux`)
- **Tags**: `manager`, `ncurses`, `pypi`, `session`, `terminal`, `tmux`

## Description

<div align="center">
  <h1>⚙️ libtmux</h1>
  <p><strong>Drive tmux from Python: typed, object-oriented control over servers, sessions, windows, and panes.</strong></p>
  <p>
    <a href="https://libtmux.git-pull.com/"><img src="https://raw.githubusercontent.com/tmux-python/libtmux/master/docs/_static/img/libtmux.svg" alt="libtmux logo" height="120"></a>
  </p>
  <p>
    <a href="https://pypi.org/project/libtmux/"><img src="https://img.shields.io/pypi/v/libtmux.svg" alt="PyPI version"></a>
    <a href="https://libtmux.git-pull.com/"><img src="https://github.com/tmux-python/libtmux/workflows/docs/badge.svg" alt="Docs status"></a>
    <a href="https://github.com/tmux-python/libtmux/actions"><img src="https://github.com/tmux-python/libtmux/workflows/tests/badge.svg" alt="Tests status"></a>
    <a href="https://codecov.io/gh/tmux-python/libtmux"><img src="https://codecov.io/gh/tmux-python/libtmux/branch/master/graph/badge.svg" alt="Coverage"></a>
    <a href="https://github.com/tmux-python/libtmux/blob/master/LICENSE"><img src="https://img.shields.io/github/license/tmux-python/libtmux.svg" alt="License"></a>
  </p>
</div>

## 🐍 What is libtmux?

libtmux is a typed Python API over [tmux], the terminal multiplexer. Stop shelling out and parsing `tmux ls`. Instead, interact with real Python objects: `Server`, `Session`, `Window`, and `Pane`. The same API powers [tmuxp], so it stays battle-tested in real-world workflows.

### ✨ Features

- Typed, object-oriented control of tmux state
- Query and [traverse](https://libtmux.git-pull.com/topics/traversal/) live sessions, windows, and panes
- Raw escape hatch via `.cmd(...)` on any object
- Works with multiple tmux sockets and servers
- [Context managers](https://libtmux.git-pull.com/topics/context_managers/) for automatic cleanup
- [pytest plugin](https://libtmux.git-pull.com/api/pytest-plugin/) for isolated tmux fixtures
- Proven in production via tmuxp and other tooling

## Requirements & support

- tmux: >= 3.2a
- Python: >= 3.10 (CPython and PyPy)

Maintenance-only backports (no new fixes):

- Python 2.x: [`v0.8.x`](https://github.com/tmux-python/libtmux/tree/v0.8.x)
- tmux 1.8-3.1c: [`v0.48.x`](https://github.com/tmux-python/libtmux/tree/v0.48.x)

## 📦 Installation

Stable release:

```console
$ pip install libtmux
```

With pipx:

```console
$ pipx install libtmux
```

With uv / uvx:

```console
$ uv add libtmux
```

```console
$ uvx --from "libtmux" python
```

From the main branch (bleeding edge):

```console
$ pip install 'git+https://github.com/tmux-python/libtmux.git'
```

Tip: libtmux is pre-1.0. Pin a range in projects to avoid surprises:

requirements.txt:

```ini
libtmux==0.50.*
```

pyproject.toml:

```toml
libtmux = "0.50.*"
```

## 🚀 Quickstart

### Open a tmux session

First, start a tmux session to connect to:

```console
$ tmux new-session -s foo -n bar
```

### Pilot your tmux session via Python

Use [ptpython], [ipython], etc. for a nice REPL with autocompletions:

```console
$ pip install --user ptpython
```

```console
$ ptpython
```

Connect to a live tmux session:

```python
>>> import libtmux
>>> svr = libtmux.Server()
>>> svr
Server(socket_path=/tmp/tmux-.../default)
```

**Tip:** You can also use [tmuxp]'s [`tmuxp shell`] to drop straight into your
current tmux server / session / window / pane.

[ptpython]: https://github.com/prompt-toolkit/ptpython
[ipython]: https://ipython.org/
[`tmuxp shell`]: https://tmuxp.git-pull.com/cli/shell/

### Run any tmux command

Every object has a `.cmd()` escape hatch that honors socket name and path:

```python
>>> server = Server(socket_name='libtmux_doctest')
>>> server.cmd('display-message', 'hello world')
<libtmux...>
```

Create a new session:

```python
>>> server.cmd('new-session', '-d', '-P', '-F#{session_id}').stdout[0]
'$...'
```

### List and filter sessions

[**Learn more about Filtering**](https://libtmux.git-pull.com/topics/filtering/)

```python
>>> server.sessions
[Session($... ...), ...]
```

Filter by attribute:

```python
>>> server.sessions.filter(history_limit='2000')
[Session($... ...), ...]
```

Direct lookup:

```python
>>> server.sessions.get(session_id=session.session_id)
Session($... ...)
```

### Control sessions and windows

[**Learn more about Workspace Setup**](https://libtmux.git-pull.com/topics/workspace_setup/)

```python
>>> session.rename_session('my-session')
Session($... my-session)
```

Create new window in the background (don't switch to it):

```python
>>> bg_window = session.new_window(attach=False, window_name="bg-work")
>>> bg_window
Window(@... ...:bg-work, Session($... ...))

>>> session.windows.filter(window_name__startswith="bg")
[Window(@... ...:bg-work, Session($... ...))]

>>> session.windows.get(window_name__startswith="bg")
Window(@... ...:bg-work, Session($... ...))

>>> bg_window.kill()
```

### Split windows and send keys

[**Learn more about Pane Interaction**](https://libtmux.git-pull.com/topics/pane_interaction/)

```python
>>> pane = window.sp

## Recent releases

| Version | Date | Urgency | Changes |
| --- | --- | --- | --- |
| `v0.58.0` | 2026-05-23 | High | libtmux 0.58.0 fixes subprocess output decoding on non-UTF-8 locales. Both `tmux_cmd` and `ControlMode` now enforce UTF-8 when reading tmux output, matching tmux's own encoding contract.  ### Fixes  #### Subprocess encoding on non-UTF-8 locales (#679)  `tmux_cmd` and `ControlMode` now pass `encoding="utf-8"` to `subprocess.Popen`, ensuring tmux output is decoded correctly regardless of the system locale. Previously, on non-UTF-8 locales, the `FORMAT_SEPARATOR` character (U+241E) was corrup |
| `v0.57.0` | 2026-05-18 | High | libtmux 0.57.0 broadens tmux support around attached clients, tmux-native filtering, and format-token fields. [`Client`](https://libtmux.git-pull.com/api/libtmux.client/) gives callers a typed object for attached terminals, `search_*()` methods let tmux return only matching sessions, windows, and panes, and more tmux format tokens are exposed as typed attributes. `LibTmuxException` now records which tmux subcommand failed, making command errors easier to handle downstream.  Full release notes: |
| `v0.56.0` | 2026-05-10 | High | The **tmux command parity** release. ~50 new public methods land across <a href="https://libtmux.git-pull.com/api/libtmux.server/"><code>Server</code></a>, <a href="https://libtmux.git-pull.com/api/libtmux.pane/"><code>Pane</code></a>, <a href="https://libtmux.git-pull.com/api/libtmux.window/"><code>Window</code></a>, and <a href="https://libtmux.git-pull.com/api/libtmux.session/"><code>Session</code></a>, plus expanded flag coverage on existing wrappers, plus a <a href="https://libtmux.git-pull |
| `0.55.1` | 2026-04-21 | Low | Imported from PyPI (0.55.1) |
| `v0.55.1` | 2026-04-19 | High | A point release focused on a pytest-plugin cleanup fix, a new Sphinx extension for documenting pytest fixtures, and a docs-stack migration to [gp-sphinx](https://gp-sphinx.git-pull.com).  ## Highlights  ### Fix: `pytest_plugin` leaks tmux socket files on teardown (#661, fixes #660)  The `server` and `TestServer` fixtures now `unlink(2)` the tmux socket from `/tmp/tmux-<uid>/` during teardown, in addition to calling `server.kill()`. tmux does not reliably remove its own socket on non-gracef |
| `v0.55.1` | 2026-04-19 | High | A point release focused on a pytest-plugin cleanup fix, a new Sphinx extension for documenting pytest fixtures, and a docs-stack migration to [gp-sphinx](https://gp-sphinx.git-pull.com).  ## Highlights  ### Fix: `pytest_plugin` leaks tmux socket files on teardown (#661, fixes #660)  The `server` and `TestServer` fixtures now `unlink(2)` the tmux socket from `/tmp/tmux-<uid>/` during teardown, in addition to calling `server.kill()`. tmux does not reliably remove its own socket on non-gracef |
| `v0.55.1` | 2026-04-19 | High | A point release focused on a pytest-plugin cleanup fix, a new Sphinx extension for documenting pytest fixtures, and a docs-stack migration to [gp-sphinx](https://gp-sphinx.git-pull.com).  ## Highlights  ### Fix: `pytest_plugin` leaks tmux socket files on teardown (#661, fixes #660)  The `server` and `TestServer` fixtures now `unlink(2)` the tmux socket from `/tmp/tmux-<uid>/` during teardown, in addition to calling `server.kill()`. tmux does not reliably remove its own socket on non-gracef |
| `v0.55.1` | 2026-04-19 | Medium | A point release focused on a pytest-plugin cleanup fix, a new Sphinx extension for documenting pytest fixtures, and a docs-stack migration to [gp-sphinx](https://gp-sphinx.git-pull.com).  ## Highlights  ### Fix: `pytest_plugin` leaks tmux socket files on teardown (#661, fixes #660)  The `server` and `TestServer` fixtures now `unlink(2)` the tmux socket from `/tmp/tmux-<uid>/` during teardown, in addition to calling `server.kill()`. tmux does not reliably remove its own socket on non-gracef |
| `v0.55.1` | 2026-04-19 | Medium | A point release focused on a pytest-plugin cleanup fix, a new Sphinx extension for documenting pytest fixtures, and a docs-stack migration to [gp-sphinx](https://gp-sphinx.git-pull.com).  ## Highlights  ### Fix: `pytest_plugin` leaks tmux socket files on teardown (#661, fixes #660)  The `server` and `TestServer` fixtures now `unlink(2)` the tmux socket from `/tmp/tmux-<uid>/` during teardown, in addition to calling `server.kill()`. tmux does not reliably remove its own socket on non-gracef |
| `v0.55.1` | 2026-04-19 | Medium | A point release focused on a pytest-plugin cleanup fix, a new Sphinx extension for documenting pytest fixtures, and a docs-stack migration to [gp-sphinx](https://gp-sphinx.git-pull.com).  ## Highlights  ### Fix: `pytest_plugin` leaks tmux socket files on teardown (#661, fixes #660)  The `server` and `TestServer` fixtures now `unlink(2)` the tmux socket from `/tmp/tmux-<uid>/` during teardown, in addition to calling `server.kill()`. tmux does not reliably remove its own socket on non-gracef |

## Citation

- HTML: https://www.freshcrate.ai/projects/libtmux
- Markdown: https://www.freshcrate.ai/projects/libtmux.md
- Dependencies JSON: https://www.freshcrate.ai/api/projects/libtmux/deps

_Generated by freshcrate.ai. Indexes pypi releases for AI-agent ecosystem packages._
