Skip to content

perf: eliminate per-query disk I/O and unblock result display from me…#216

Open
thomaswasle wants to merge 1 commit into
TabularisDB:mainfrom
thomaswasle:feature/query-execution-speed
Open

perf: eliminate per-query disk I/O and unblock result display from me…#216
thomaswasle wants to merge 1 commit into
TabularisDB:mainfrom
thomaswasle:feature/query-execution-speed

Conversation

@thomaswasle
Copy link
Copy Markdown
Contributor

Problem

Two independent issues were adding latency to every query execution:

  1. Connections file read on every query (backend)

find_connection_by_id — called for every query, export, explain, schema command, etc. — unconditionally read and
parsed the entire connections JSON file from disk using blocking std::fs::read_to_string on a Tokio worker thread.
On SSH connections, expand_ssh_connection_params triggered a second file read for the SSH config. This happened even
when the connection hadn't changed.

  1. Column/FK metadata fetch blocking result display (frontend)

After each query completed, runQuery awaited fetchPkColumn — which fires parallel get_columns + get_foreign_keys
backend calls — before calling updateTab with the query result. The result grid was invisible until both metadata
requests finished. On a remote database, those two information_schema round-trips could add 100–500 ms of perceived
query latency.

Changes

src-tauri/src/connection_cache.rs (new)

Introduces ConnectionCache: a Mutex<Option<HashMap<String, SavedConnection>>> registered as Tauri state. Exposes
three operations:

  • lookup(id) — returns Hit, Miss, or Cold in a single lock acquisition
  • populate(&[SavedConnection]) — fills the map on a cold miss
  • invalidate() — drops the map after any write to the connections file

src-tauri/src/commands.rs

  • find_connection_by_id now checks the cache first. A cache hit is an O(1) HashMap lookup with no disk I/O. A cold
    miss reads the file once and warms the cache for all subsequent calls.
  • New save_connections_and_invalidate helper wraps every persistence::save_connections_file call and drops the cache
    afterwards, so stale data is never served. Replaces all 12 call sites.

src/pages/Editor.tsx

Reorders the post-query flow so updateTab with the result fires immediately after the query returns. fetchPkColumn
is then started without await — it updates pkColumn, columnMetadata, and foreignKeys in the background via its own
updateTab call. Both updates target independent tab keys, so the React functional state updater merges them
correctly without races.

Notes

  • The connection cache is intentionally whole-map invalidated (not per-key updated) on writes. Connections are saved
    infrequently; the simplicity is worth it.
  • fetchPkColumn already handles its own errors and calls updateTab({ pkColumn: null }) in its catch block, so
    removing the await does not affect error handling.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant