Skip to content

Fix MySQL autocomplete in multi-database setups#184

Open
Maxteabag wants to merge 1 commit intomainfrom
autocomplete-mysql-multidb
Open

Fix MySQL autocomplete in multi-database setups#184
Maxteabag wants to merge 1 commit intomainfrom
autocomplete-mysql-multidb

Conversation

@Maxteabag
Copy link
Copy Markdown
Owner

Closes #151.

Surfaced two bugs by stress-testing autocomplete against a real MySQL 5.7 container with two user databases, across seven cursor positions per scenario.

Bug 1 — malformed qualified names in multi-db mode:
Tables rendered as `inventory`..shipments `` — an empty-backticked schema slot between db and table. MySQL has no schema-within-database, so the schema string is ""; the inline name-builder inserted it unconditionally. Factored a `_qualify_table_name` helper that skips empty segments; routed all four call sites (tables/views × sync/async loader) through it.

Bug 2 — autocomplete wedged on Loading... for schema-qualified partials:
Typing SELECT * FROM shop.cu parses shop as an ALIAS_COLUMN scope. That key isn't in _table_metadata, so _load_columns_for_table('shop') skips silently — but the suggestion engine had already returned the Loading... sentinel, and kept returning it on every subsequent call. Guard the sentinel on the table key actually existing in metadata.

Matrix results (before → after) for the worst scenario (no default database, two user DBs indexed):

Cursor state Before After
After FROM `inventory`..shipments ``, … `inventory`.`shipments`, …
FROM shop. ['Loading...'] forever customers, orders, products
FROM shop.cu ['Loading...'] forever `shop`.`customers`
FROM inventory.wa ['Loading...'] forever `inventory`.`warehouses`
FROM customers WHERE em email, … (already ok) email, … (unchanged)

7 new unit tests pin the name-builder across dialects (MySQL-style no schema, Postgres-style schema-only, SQL Server-style db+schema, both empty, embedded backticks) and the stuck-Loading regression. Full unit suite 823 tests green.

Two bugs surfaced by driving the TUI's completion engine against a real
MySQL server with multiple user databases:

1. Qualified table/view names rendered as `db`.``.`table`. MySQL has no
   schema-within-database, so the schema slot comes back as ''; the
   inline name-builder inserted it unconditionally, producing a
   three-part identifier with an empty middle. Promote the composition
   rule to a new `Dialect.qualified_name(database, schema, name)`
   method. Base default skips empty segments, which yields the correct
   result for every current adapter:
     MySQL/MariaDB: `db`.`table`
     PostgreSQL:    "schema"."table"
     SQL Server:    [db].[schema].[table]
     SQLite:        "table"
   Autocomplete's four inline builders (tables/views × sync/async
   loader) now call `dialect.qualified_name(...)` directly.

2. Completions stuck on "Loading..." for cursor positions like
   `SELECT * FROM shop.cu`. The completion engine classifies this as
   an ALIAS_COLUMN with scope 'shop', which isn't a real table. The
   loader skips unknown keys silently; the caller kept returning
   Loading... forever because the guard assumed "not yet loaded" meant
   "in flight". Guard the sentinel on the table key actually existing
   in `_table_metadata`.

Covered by 8 new unit tests pinning `qualified_name` on MySQL,
MariaDB, PostgreSQL, SQL Server, empty-segment behavior, quote-char
escaping, and the stuck-Loading regression.

May fix #151.
@Maxteabag Maxteabag force-pushed the autocomplete-mysql-multidb branch from b70acf4 to a3a28dc Compare April 19, 2026 14:04
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.

Autocomplete doesnt work on table names in MyQSL

1 participant