Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
17 changes: 17 additions & 0 deletions docs.json
Original file line number Diff line number Diff line change
Expand Up @@ -415,6 +415,23 @@
}
]
},
{
"tab": "Linux",
"icon": "linux",
"groups": [
{
"group": "TablePro for Linux",
"pages": [
"linux/install",
"linux/connect",
"linux/sql-editor",
"linux/data-grid",
"linux/keyboard-shortcuts",
"linux/troubleshooting"
]
}
]
},
{
"tab": "Developers",
"icon": "code",
Expand Down
4 changes: 2 additions & 2 deletions faq.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -91,8 +91,8 @@ Through iCloud, with a Pro or Team license. Sync is off by default and each cate
Yes, for iPhone and iPad on iOS 18 or later. It reads the same CloudKit data as the Mac app but carries connections, groups, and tags only. See [iPhone and iPad](/ios).
</Accordion>

<Accordion title="Is there a Windows or Linux version?">
No, macOS and iOS only. A Linux port is a prototype with nothing to install yet, and there is no Windows build at all. Progress is tracked on [GitHub](https://github.com/TableProApp/TablePro).
<Accordion title="Is there a Linux version?">
Yes, in beta: packages for Ubuntu 26.04 and 26.10 and Fedora 44 and later, and a Flatpak bundle for other distributions. It is a separate app with its own [engines](/linux/connect#engines), and none of the [paid features](/features/licensing) yet. See [Install on Linux](/linux/install).
</Accordion>

<Accordion title="How often does TablePro release, and will it keep interrupting me?">
Expand Down
4 changes: 4 additions & 0 deletions features/licensing.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,10 @@ There are two tiers, Pro and Team. Team includes everything in Pro. Starter was
| [Team Catalog](/features/connection-sharing) | Team | Menu item hidden |
| [Team Library](/features/team) | Team | Menu item hidden |

The [Linux beta](/linux/install) follows the same licensing model as the Mac. The paid features listed here are Mac-only for now and come to Linux later.

The activation instructions on this page apply to the Mac.

**Settings > License** lists these features under **Pro Plan** and **Team Plan** and marks each plan your license includes. On a Pro license, **Upgrade Plan** sits beside **Team Plan**. Everything else in the app works.

The **Activate License…** dialog also links to the pricing page. A license you already hold never gets that offer: every gate says what the top of **Settings > License** says for its state, so an expired license offers **Renew License**, a suspended one says so, and one that has not reached the server in 30 days offers **Try Again**.
Expand Down
Binary file added images/linux-connect-dialog-dark.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added images/linux-connect-dialog.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added images/linux-data-grid-dark.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added images/linux-data-grid.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added images/linux-shortcuts-dialog-dark.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added images/linux-shortcuts-dialog.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added images/linux-sql-editor-dark.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added images/linux-sql-editor.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
4 changes: 2 additions & 2 deletions index.mdx
Original file line number Diff line number Diff line change
@@ -1,11 +1,11 @@
---
title: Introduction
description: Native macOS database client for MySQL, PostgreSQL, SQLite, MongoDB, Redis, and 42 more
description: Native database apps for Mac, iPhone, iPad and Linux (beta)
---

import DriverCounts from "/snippets/driver-counts.mdx";

Every engine, the SQL editor, the data grid, import, export, and the AI assistant cost nothing, and there is no trial countdown. Paid tiers cover iCloud sync, encrypted connection export, environment variables in connection fields, Linked Folders, Query Insights, result charts, and team sharing ([Licensing](/features/licensing)). Mac is the full app, [iPhone and iPad](/ios) run a smaller one, and there is no Windows or Linux build.
Every engine, the SQL editor, the data grid, import, export, and the AI assistant cost nothing, and there is no trial countdown. Paid tiers cover iCloud sync, encrypted connection export, environment variables in connection fields, Linked Folders, Query Insights, result charts, and team sharing ([Licensing](/features/licensing)). Use the Mac app, the [iPhone and iPad app](/ios), or the [Linux beta](/linux/install). Paid features are Mac-only for now.

<Frame caption="TablePro - Native macOS Database Client">
<img className="block dark:hidden" src="/images/app.png" alt="TablePro main interface" />
Expand Down
144 changes: 144 additions & 0 deletions linux/connect.mdx
Original file line number Diff line number Diff line change
@@ -0,0 +1,144 @@
---
title: Connect
description: The engines, the connect dialog, TLS, SSH tunnels and SQLite or DuckDB files in TablePro for Linux
tag: "Beta"
---

A window holds several connection sessions and their tabs. The selected tab decides the active connection for window actions, banners and the assistant. Check its connection and database labels before running a query or changing data.

Opening a connection that is already open brings its window and session forward. **New Window** (`Ctrl+Shift+N`) starts another with the connection list. **Open Database…** on a connection's sidebar row opens another database as a session in the same window.

<Frame caption="A PostgreSQL connection through an SSH tunnel">
<img className="block dark:hidden" src="/images/linux-connect-dialog.png" alt="The connect dialog with Connection, Authentication, Security, SSH Tunnel and Options groups for a PostgreSQL server" />
<img className="hidden dark:block" src="/images/linux-connect-dialog-dark.png" alt="The connect dialog with Connection, Authentication, Security, SSH Tunnel and Options groups for a PostgreSQL server" />
</Frame>

## Engines

Every driver is compiled into the app. Pick the one in **Driver**:

| Engine | Driver | Default port |
|---|---|---|
| PostgreSQL | **PostgreSQL** | 5432 |
| MySQL and MariaDB | **MySQL** | 3306 |
| SQL Server | **SQL Server** | 1433 |
| ClickHouse | **ClickHouse** | 8123 |
| Cassandra and ScyllaDB | **Cassandra / ScyllaDB** | 9042 |
| Redis | **Redis** | 6379 |
| MongoDB | **MongoDB** | 27017 |
| SQLite | **SQLite** | No port: a file |
| DuckDB | **DuckDB** | No port: a file |

The server releases each engine is tested against, and the ones it does not support, are in the app's [supported servers](https://github.com/TableProApp/TablePro/blob/main/linux/README.md#supported-servers) table.

Redshift, CockroachDB, TiDB, OceanBase and Databend are untested on Linux. Support through the PostgreSQL or MySQL drivers on Mac does not establish Linux compatibility.

## Limits

- Binary, array, spatial, composite and variant cells are read-only. Inspect or copy them in the grid; use a query to change them.
- Enter time and timestamp values as text, such as `13:45:00` or `2026-11-05 13:45:00`. Include an offset for types that store one. Invalid values stay in the editor with an error; correct them before saving.
- Redis Cluster and Sentinel are unsupported. Connect to a standalone Redis server instead.

## Add a connection

<Steps>
<Step title="Open the connect dialog">
Click **Add Connection** in an empty connection list, or choose **New Connection…** from the main menu.
</Step>
<Step title="Name the server">
Pick the **Driver**, then fill **Host** and **Database**. **Port** starts on the engine's default.
</Step>
<Step title="Sign in">
Fill **Username** and **Password**. With **Remember Password** on, the password goes to [secret storage](/linux/troubleshooting#passwords); with it off, every connect asks for it.
</Step>
<Step title="Test, then connect">
**Test** connects once to check the settings, then disconnects. **Connect** saves the connection and adds its session to the window.
</Step>
</Steps>

For a MongoDB replica set or cluster behind a `mongodb+srv://` address, turn on **DNS Seed List**. **Authentication Database (optional)** names the database that holds the user.

## Options

| Row | Sets |
|---|---|
| **Safe Mode** | What is asked before a write. See the next table |
| **External Clients** | What MCP clients may do on the connection: **Blocked**, **Read Only** (the default) or **Read & Write** |
| **AI Assistant** | Whether the assistant may send anything from the connection: **Ask Each Time** (the default), **Allow** or **Never** |
| **Custom Query Timeout** | An editor timeout for this connection in place of the one in Preferences. 0 turns it off |

Safe Mode is also in the main menu while connected, and a change there is saved to the connection.

| Safe Mode | Does |
|---|---|
| **Off**, the default | Asks only before DROP, TRUNCATE, and DELETE or UPDATE without WHERE |
| **Confirm Writes** | Asks before every statement that changes the database, showing the SQL and the connection |
| **Read-Only** | Opens the connection read-only, and refuses every editor statement that does not read |

Pick **Read-Only** for a production server you only read. Moving to or from it reconnects that connection's sessions.

## TLS

**Encryption** under **Security** picks the mode:

| Mode | Connection |
|---|---|
| **Disable** | Plain, no TLS |
| **Require** | Encrypted. The server certificate is not checked |
| **Verify full**, the default | Encrypted. The certificate must be valid for the server name |
| **Strict** | SQL Server only. TLS before the login, as TDS 8.0 needs. SQL Server 2022 or later on Windows, 2025 or later on Linux |

Keep **Verify full** unless the server has no certificate this computer can check. For a server signed by your own certificate authority, choose its PEM file in **CA certificate** rather than dropping to **Require**.

- **Client certificate** and **Client key** log in with a certificate, on every network engine but SQL Server.
- **TLS server name** checks the certificate against another name than the host. MySQL and MongoDB take it only through an SSH tunnel.
- A failed handshake says what went wrong. An unknown issuer takes you to **CA certificate**, a name mismatch to **TLS server name**.

## SSH tunnels

Turn on **Use SSH Tunnel** and fill **Host or alias**. Native packages run the system `ssh` client, so empty rows come from `~/.ssh/config`, and `known_hosts` and your SSH agent apply as they do in a terminal. For the bundle, check [Flatpak connections](#flatpak-connections).

| Authentication | Uses |
|---|---|
| **SSH agent** | Keys from the SSH agent and your SSH configuration |
| **Private key** | A key file, unlocked with **Passphrase** if it has one |
| **Password** | The SSH server's own password |
| **Keyboard-interactive** | The SSH server's own questions, such as a one-time code |

Use **SSH agent** by default. Choose **Private key** for a specific key file, or **Password** or **Keyboard-interactive** when the server requires it.

**Jump hosts** takes what `ssh -J` takes: `user@host:port`, several separated by commas.

An unknown or changed host key shows its SHA256 fingerprint before anything connects, even where `ssh_config` says `StrictHostKeyChecking accept-new` or `no`. [Troubleshooting](/linux/troubleshooting#ssh-tunnels) covers a changed or revoked key.

## SQLite and DuckDB files

With **SQLite** or **DuckDB** picked, **Database file** replaces the server rows. **Choose…** opens an existing file, and **New Database…** creates the file when you connect.

A file also opens straight from Files, through **Open With** on a SQLite database, or from a terminal:

```bash
tablepro app.sqlite3 sales.duckdb
```

The file's own header picks the engine, whatever its name. Each file opens as a session. A file on a network or FUSE filesystem asks whether to open it read-only first, because neither engine's locking holds there.

## SQL Server with Kerberos

Set **Method** to **Windows (Kerberos)**. There is no username or password: the driver uses the ticket `klist` shows, so get one first.

```bash
kinit you@EXAMPLE.COM
```

The driver asks for `MSSQLSvc/<host>:<port>` from the host and port you typed. Native packages use the default realm of the host's `/etc/krb5.conf`. Type the host name the SPN is registered for, not an IP address or a CNAME. A server in another realm works only when your KDC answers with a referral, as Active Directory does inside a forest.

## Flatpak connections

The bundle runs inside a sandbox. Check these differences before copying a native connection setup:

- Secrets use the Secret portal and an encrypted file inside the sandbox. Follow [keyring recovery](/linux/troubleshooting#passwords) if a password, MCP token or AI key cannot be stored.
- Kerberos uses the host's KCM ticket cache. The sandbox selects `/app/etc/krb5.conf`, with DNS realm and KDC lookup, instead of the host's `/etc/krb5.conf`. Obtain a ticket in KCM on the host; a file-backed ticket cache is not enough.
- SSH reads `~/.ssh/config`, keys and `known_hosts`, but not the host's `/etc/ssh` configuration. `ProxyCommand` and `Match exec` cannot run host-only helpers. Use a setup supported inside the sandbox or install a native package.
- File-backed FIDO keys cannot sign inside the sandbox. Load the key into the host SSH agent and choose **SSH agent**.
- A CA installed only on the host is absent from the runtime's trust store. Select its PEM file in **CA certificate** and keep **Verify full**.
68 changes: 68 additions & 0 deletions linux/data-grid.mdx
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@
---
title: Data grid
description: Page through a table, filter and sort it on the server, edit rows and save them together in TablePro for Linux
tag: "Beta"
---

A table opened from the sidebar fills a table tab one page at a time, 1,000 rows by default. The bottom bar switches the tab between 100 and 10,000 rows per page, and **Preferences > General > Default page size** sets where new tabs start.

<Frame caption="An edited cell and a new row wait in the pending changes bar until Save">
<img className="block dark:hidden" src="/images/linux-data-grid.png" alt="A table tab with a filter rule above the grid, one modified cell, one new row and the pending changes bar with Discard and Save" />
<img className="hidden dark:block" src="/images/linux-data-grid-dark.png" alt="A table tab with a filter rule above the grid, one modified cell, one new row and the pending changes bar with Discard and Save" />
</Frame>

## Pages and row counts

`Alt+Page Down` and `Alt+Page Up` move between pages. A table of about 100,000 rows or fewer is counted on its own; a larger one shows an estimate and offers **Count Rows** for the exact number.

A MongoDB collection opens in a table tab too: its top-level fields are the columns, `_id` first, and nested documents and arrays show as JSON.

## Sort and filter

Click a column header to sort by it, one column at a time. In a table tab the server sorts the whole table; in query results the grid sorts the rows it holds. A Cassandra or ScyllaDB table keeps the server's order.

`Ctrl+F`, or **Filter Rows**, opens the filter bar over the grid:

- Each rule is a column, an operator and a value. **Match** chooses whether any or all of them have to hold.
- In place of rules, type a WHERE fragment such as `created_at > now() - interval '1 day'`. It is checked as one expression before it runs. On MongoDB it is a query document instead.
- **Filter by Value** and **Exclude Value** in a cell's menu add a rule from that cell.
- On Cassandra and ScyllaDB the filter offers only the operators the server evaluates, all of them matched, with `ALLOW FILTERING`.

A table's filter is kept, and so is each tab's across a restart.

## Edit rows

Editing works in a table tab on a table with a primary key. Rows a query returns in the SQL editor are read-only, and so are key, generated and auto-increment columns. Check the [cell type limits](/linux/connect#limits) before editing other columns.

| To | Press |
|---|---|
| Edit the focused cell | `F2` or `Enter` |
| Toggle a boolean cell | `Space` |
| Set the cell to NULL | `Ctrl+Backspace` |
| Insert a row | `Ctrl+N` |
| Mark the selected rows for deletion | `Delete` |
| Edit a long value, or the whole row | `Alt+Enter` for **Row Details** |
| Undo or redo a change | `Ctrl+Z`, `Ctrl+Shift+Z` |

Dates get a calendar, and JSON is checked before it is kept. A date, time or timestamp cell also takes the engine's own `NOW()`, `CURRENT_TIMESTAMP` and the like, typed in or picked from the cell's menu.

`Ctrl+V` with tab-separated rows on the clipboard adds them as new rows, filling the columns from the focused one, or by name when the first line holds the headers. More than 1,000 rows asks first, and 100,000 is the most one paste takes.

## Save or discard

Every change waits in the pending changes bar. **Save** (`Ctrl+S`) writes them together, in one transaction where the engine has them, and **Discard** drops them. Deleting 10 rows or more asks first, unless **Confirm Before Deleting Rows** is off under **Preferences > General**.

On ClickHouse, Cassandra and ScyllaDB a save is a series of statements, each landing on its own. **Stop Saving** there takes effect between statements.

## Copy and export

`Ctrl+C` copies the focused cell or the selected rows. **Copy As** in the cell's menu writes them as CSV, JSON, JSON Lines, Markdown, a text table or an `IN` clause, and in a table tab as `INSERT` statements.

**Export Rows…** writes CSV, JSON, Markdown, HTML, XML, Excel or SQL `INSERT` to a file, from the current page with its pending edits or from every saved row under the filter and sort.

## Columns and foreign keys

- `Alt+Left` and `Alt+Right` move the focused column, and `Shift+Alt+Left` and `Shift+Alt+Right` narrow and widen it. Dragging a header moves the column, and dragging its edge resizes it.
- **Columns…** hides and shows columns. **Reset Columns** there goes back to the table's own order.
- Order, hidden columns and widths are kept per table.
- `Ctrl+J` on a foreign key cell opens the row it points at in a new tab. **Show Referencing Rows** on a saved row opens the rows that point at it.
Loading
Loading