The broadcast channels you own, as a familiar desktop file manager. Read-only on Telegram · virtual folders that live only on your machine · 100% local, append-only.
Features · Quick start · Drive mount · How it works · Stack · Safety · Development
Marco Tagliaferri — PhD Candidate in Neuroscience 🏛️ Center for Mind/Brain Sciences (CIMeC), University of Trento, Italy
Corbula shows only the channels you own and the media inside them, and lets you organise that media into virtual folders stored in a local SQLite database. Telegram is never modified — the single write the app can make is uploading a file into a channel you bind to a folder.
Note
You saved movie.avi in a private channel. Corbula lets you drag it into a virtual Videos/ folder. On Telegram, the file never moves.
- Your channels only — broadcast channels you created, plus Saved Messages. Hide, drag-reorder, recolour.
- Media-first listings — photos, videos, documents, audio; text posts skipped. Infinite scroll, full-channel search, grid or list views.
- In-app viewer, zero disk — images, PDFs, video and audio stream straight into the window. mp4/webm play natively; mkv/avi remux on the fly via
ffmpeg; H.264 and H.265 are stream-copied, never re-encoded. - Open in VLC — any video opens in VLC from the local stream: instant seeking, every codec, all audio/subtitle tracks.
- Folder sync across machines — opt-in, mirror your folder structure between your computers through your own Telegram (Saved Messages by default, or any channel you own). Edits converge (last-writer-wins); an import overwrites and re-syncs everywhere. Read-only on your channels — only tiny structure files are written, and they're hidden from the in-app listing.
- Whole-library search — one Search place queries every bookmarked file by name, type or size, with no Telegram round-trip.
- Filters — narrow any view by file type and size range; stacks with search and sort.
- Virtual folders — nested bookmark folders; files link in (never copy), subfolders open as tiles, drag to reorder and nest in or out at any level, empty contents in one action.
- Copy / cut / paste — organise like a file manager: Ctrl+C / Ctrl+X / Ctrl+V (or the right-click menus) to copy or move files between folders, selection-aware and undoable. Still only links — Telegram is never touched.
- Undo / redo — Ctrl+Z / Ctrl+Y across all file and folder actions, including folder delete with full subtree restore. Never touches Telegram.
- Upload to a bound channel — bind a folder to a channel; uploads land there and auto-link back. The app's only Telegram write.
- Track pickers — switch audio and subtitles mid-playback, in-app or in VLC.
- Transfers you control — cancellable progress toasts; download one file, reveal it in the file manager, or a whole folder sequentially.
- App lock — optional passcode (salted hash) with auto-lock; gates the local API server-side, rate-limits attempts, unmounts the drive while locked, and never cuts off active playback.
- Storage limit — self-imposed cap on the bookmarked library, with warnings and upload refusal past it.
- Native shell — menubar, breadcrumbs, back/forward, dark UI. Closing the window keeps Corbula alive in the tray (Windows/Linux) or Dock (macOS).
- Drive mount (optional) — browse bookmarks as an append-only native volume from any file manager. → details
Tip
For long videos, prefer VLC over the built-in player. VLC decodes every codec natively and seeks instantly, while the built-in player transcodes mkv/avi.
- On Windows: use right-click → Open in VLC from inside the app. It feeds VLC Corbula's seek-friendly local stream — faster than the built-in player and than opening the file off the mounted drive (where every seek reopens the download).
- On Linux / macOS: opening a video with VLC straight off the mounted drive is essentially identical to the in-app Open in VLC — either works equally well.
A living map of your channels. Home lays out channels and folders as a force-directed constellation — sphere size tracks content volume, links trace nesting and upload bindings. Drag to rearrange, scroll to zoom, right-drag to pan, click to open.
Home constellation — channels and folders as a force-directed graph; drag, zoom, pan, click to open.
Install your platform's prerequisites before running Corbula — prebuilt or from source.
Linux (Debian / Ubuntu 24.04+)
Prebuilt (AppImage) — the .deb installs these as dependencies automatically:
sudo apt install \
libwebkit2gtk-4.1-0 gir1.2-gtk-3.0 gir1.2-webkit2-4.1 \
gir1.2-ayatanaappindicator3-0.1 \
gstreamer1.0-plugins-good gstreamer1.0-libavFrom source — adds the dev headers for the PyGObject build:
sudo apt install \
libgirepository1.0-dev libcairo2-dev pkg-config \
libwebkit2gtk-4.1-0 gir1.2-gtk-3.0 gir1.2-webkit2-4.1 \
gir1.2-ayatanaappindicator3-0.1 \
gstreamer1.0-plugins-good gstreamer1.0-libavOptional:
| Package | Purpose |
|---|---|
ffmpeg |
mkv / avi in-app playback |
vlc |
Open in VLC |
libfuse-dev |
Drive mount (uv sync --extra mount) — libfuse itself is preinstalled on most distros |
| GNOME Keyring or KWallet | Secret Service keyring backend (present on standard desktops) |
Tray: GNOME needs an AppIndicator host (
gir1.2-ayatanaappindicator3-0.1, included above) plus a shell extension. AppIndicator has no double-click action: re-open via the tray menu's Open Corbula.
Linux (Fedora)
From source:
sudo dnf install \
gobject-introspection-devel cairo-gobject-devel pkgconf-pkg-config \
gtk3 webkit2gtk4.1Optional: same as Debian / Ubuntu above (ffmpeg, vlc, fuse-devel for the drive mount).
macOS
No system packages needed — pywebview uses the built-in WKWebView. HEVC decodes natively.
Optional:
| Package | Purpose |
|---|---|
ffmpeg |
mkv / avi in-app playback (brew install ffmpeg) |
| VLC | Open in VLC |
| macFUSE or FUSE-T | Drive mount (uv sync --extra mount) |
Windows
No system packages needed.
Optional:
| Package | Purpose |
|---|---|
ffmpeg on PATH |
mkv / avi in-app playback |
| VLC | Open in VLC |
| WinFsp | Drive mount (uv sync --extra mount; needs Python 3.11) |
| HEVC Video Extensions | H.265 in the built-in player |
Each release ships per-OS builds from the Build Releases workflow (also runnable on demand from the Actions tab). No Python required; same streaming engine as a source run.
- Windows —
Corbula-<ver>-windows-x64.exe, single portable executable. - macOS —
Corbula-<ver>-macos-arm64.dmg(Apple Silicon only). Unsigned: first launch needs right-click → Open. - Linux —
Corbula-<ver>-x86_64.AppImageorCorbula_<ver>_amd64.deb(sudo apt install ./Corbula_*.deb). Needs glibc ≥ 2.39 (Ubuntu 24.04+).
Prerequisites — Python 3.11+ and
uv. On Linux, install the system packages first.
git clone https://github.com/marcotag93/Corbula.git
cd Corbula
uv sync --extra dev
uv run corbula- Paste your
api_id+api_hashfrom my.telegram.org/apps. - Enter your phone number (
+…), the login code, and your 2FA password if set.
The session is cached at ~/.corbula/session.dat; later launches go straight to the app home. Credentials live in the OS keyring, never on disk in plain text.
- HEVC in the built-in player — Windows needs the HEVC Video Extensions codec; macOS decodes natively; Linux usually falls back to re-encode (or use Open in VLC for original quality and better streaming).
Mount your bookmark folders as an append-only native volume and browse them from any file manager or open dialog. Install the platform driver, run uv sync --extra mount, then Settings → Mount as Drive. Default mount point: T: drive on Windows, ~/CorbulaDrive on Linux / macOS.
On the drive: browse, open and copy out anywhere; copy a file in to upload it to the folder's bound channel; delete to remove the bookmark link (the Telegram message stays — deletes are permanent, Trash is refused); create/rename/move folders. In-place edits, overwrites and file renames are rejected. Indexer junk is suppressed and concurrent downloads are capped, so a thumbnail-happy file manager can't flood your account.
Read speed: both the GUI and the mount pull from the same single Telethon stream — raw throughput is your Telegram link speed. The mount serves raw bytes, so seeking players reopen the download on every jump. On Windows prefer the GUI for video (built-in viewer or Open in VLC), which avoids that. On Linux / macOS opening a video with VLC directly off the mounted drive performs essentially the same as the in-app Open in VLC, so either is fine.
Testing —
python scripts/mount_spike.pymounts a fake tree (no Telegram, no DB) through the real driver and asserts reads and append-only writes;--benchmeasures throughput. It is deliberately a standalone script, not a pytest test: a real kernel volume is global OS state CI can't provide, and a hung bring-up needs an operator watching. The mount logic itself is unit-tested intests/.
Corbula speaks MTProto directly with your user account through Telethon — no bot, no intermediary server. Listings and media bytes are read on demand; nothing is mirrored to disk unless you download it. Your organisation (folders, colours, ordering, hashed passcode) lives in one local SQLite database. The viewer and the drive mount share the same single Telethon stream, so both run at your Telegram link speed — backed by cryptg (native AES-IGE, ~15× faster than the pure-Python fallback) on every path, GUI or mount. For long videos, prefer VLC over the built-in player. On Windows, use Open in VLC from inside the app: it streams Corbula's seek-friendly local stream rather than the raw mount bytes, so seeks don't reopen the download. On Linux / macOS, opening from the mounted drive with VLC is essentially equivalent to the in-app Open in VLC.
Folder sync (optional). With no server to lean on, syncing your folder structure between machines rides on Telegram itself: each change is appended as a tiny JSON write-ahead-log segment in your Saved Messages (the default) or any channel you own that you pick in Settings → Security → Folder sync. Other machines pointed at the same chat read the segments newer than they've seen and merge them last-writer-wins, so concurrent edits converge; an import bumps a generation counter and replaces the structure everywhere. Folder identities are machine-independent ids, your channels are never modified, and the sync blobs are hidden from Corbula's listing.
| Layer | Technology |
|---|---|
| Telegram client | Telethon — MTProto, user session |
| Backend | FastAPI + Uvicorn, bound to 127.0.0.1 |
| Database | SQLite via SQLAlchemy 2.0 async + Alembic |
| Desktop shell | pywebview |
| Frontend | GNOME Adwaita-style static HTML / CSS / JS |
| Media | ffmpeg (optional — mkv/avi in-app playback) |
| Drive mount | WinFsp + winfspy (Windows) · FUSE via fusepy (Linux, macOS) — optional |
| Crypto | cryptg — native AES-IGE, ~15× faster than the pure-Python fallback |
| Secrets | OS keyring |
- Append-only on Telegram. The single write is
send_file(folder upload), confined totelegram/uploader.py; edit / delete / forward / pin are never wired. The drive mount obeys the same rule. - Only your channels. Dialogs are filtered server-side to broadcast channels you created; nothing else reaches the UI.
- Local state. Folders, settings and the passcode verifier (salted PBKDF2, never plain text) live in
~/.corbula/corbula.sqlite3. - No disk writes for viewing. Media streams over
127.0.0.1into the window; only an explicit Download persists a file. - Credentials stay in the OS keyring; the Telethon session file is the only sensitive on-disk artifact (permissions tightened to
0600on launch). The passcode gates the UI and the local API, which also rejects foreignHostheaders — but it is not encryption. - Hardened webview. Strict Content-Security-Policy (
script-src 'self',connect-src 'self'); the desktop bridge exposes only Quit, a user-confirmed Save dialog and a user-confirmed folder picker.
uv run ruff check .
uv run black --check .
uv run mypy src
uv run pytestCoverage gate: ≥ 80%. A guard test (tests/test_no_mutation.py) fails the build if any write-capable Telegram call appears outside the allowlisted send_file in telegram/uploader.py.
src/corbula/
__main__.py # pywebview launcher
app.py # FastAPI factory
config.py # Settings + keyring-backed credentials
telegram/ # Telethon wrapper (client, auth, readers, uploader)
db/ # SQLAlchemy models, Alembic, repositories
services/ # business logic
api/v1/ # HTTP routers
mount/ # optional native drive (WinFsp / FUSE)
ui/ # static HTML/CSS/JS
tests/ # unit + integration + guard
.github/
workflows/ # CI + Build Releases (per-OS packaging)
packaging/ # PyInstaller spec + launcher + icons + desktop file
Unofficial third-party client — not affiliated with, authorised, or endorsed by Telegram. You run it with your own API credentials and are bound by Telegram's API Terms of Service. Automating a user account can, if abused, lead to rate-limiting or account restrictions. Provided "as is", without warranty.
Use it wisely. Corbula organises media you already keep on Telegram — it is not a tool for hoarding or for treating Telegram as a free infinite drive. The built-in storage limit (Settings → Security) is there to help. You alone are responsible for the content you store, upload or access through your account.
WinFsp, macFUSE / FUSE-T and libfuse are separate drivers you install yourself; none is bundled or redistributed here.
