GeezerVison is showing github.com — Share MySQL account names across CREATE USER and DEFINER by minleejae · Pull Request #2806 · JSQLParser/JSqlParser
Conversation
minleejae
commented
Oct 14, 2026
•
edited
Loading
Uh oh!
There was an error while loading. Please reload this page.
Purpose
Read MySQL account names (user[@host]) with one grammar rule wherever they appear. Today, CREATE USER and the view, trigger and routine DEFINER clause each repeat the same rule, and both miss spellings that MySQL accepts:
CREATE USER app@'%' and CREATE USER 'app'@localhost fail. The lexer reads app@ and @localhost as single tokens, and neither rule splits them.
- Without a dialect,
CREATE USER "app"@"%" IDENTIFIED BY 'x' renders as CREATE USER app@% IDENTIFIED BY 'x', which is not valid SQL. The double quotes are dropped.
- A backquoted part keeps its backquotes inside the value (
`app`), while a single-quoted part keeps only its text (app).
The account statements and GRANT/REVOKE changes that follow build on this rule.
Current design (As-is)
MySqlUserAccount() (CREATE USER) and MySqlDefiner() both read MySqlAccountNamePart() [@ MySqlAccountNamePart()].
MySqlAccountNamePart() turns an identifier into new StringValue(name). That constructor strips double quotes, and the result is then marked unquoted.
Target design (To-be)
- Add one production,
MySqlAccountName(), that returns a UserAccount with separate user and host parts. It accepts every spelling:
- each part unquoted or quoted with
', " or a backquote;
- the lexer-merged forms
app@localhost, app@'%' and 'app'@localhost, which it splits into user and host.
MySqlUserAccount() (CREATE USER) and MySqlDefiner() use it. Their models are unchanged: UserAccount and MySqlDefiner keep getUser()/getHost().
- A double-quoted or backquoted part keeps its quote character in
getQuoteStr() and its text in getValue(), the same way a single-quoted part already did. CREATE USER "app"@"%" now renders unchanged in every mode.
DEFINER = CURRENT_USER[()] is unchanged.
- Document the account names in the usage guide.
Compatibility: rendered SQL is unchanged, except for the double-quoted accounts that previously lost their quotes. In the AST:
- A backquoted part now has the value
app with quote `, instead of the value `app`.
- An unquoted
app@localhost is now split into user app and host localhost. Before, it was one user named app@localhost without a host.
Validation
- New
MySqlAccountNameTest, 25 cases. Ten spellings each go through CREATE USER (with Dialect.MYSQL and without a dialect), view DEFINER and trigger DEFINER, with exact toString() and StatementDeParser output and the user/host value and quote character. It also checks rejected forms (app@, @host, 'app'@) and the unchanged DEFINER = CURRENT_USER().
- Java 17 offline Gradle
spotlessApply check: 10,377 tests, 10,352 passed, 25 skipped, zero failures/errors. The grammar choice conflict check passes.
- MySQL 8.4: ran 12 CREATE USER, DEFINER view/trigger and lookup statements in original and rendered form on two identical servers. The results match, and the created accounts and definers are identical:
app2@'%', 'app3'@localhost, `app4`@`%`, "app5"@"%", …
- A corpus of 635 MySQL 8.4 / PostgreSQL 18 DDL and DCL statements, each accepted by the server: parse results are unchanged from
master. On two servers per database, the rendered SQL gives the same results as the original for all 205 MySQL and 327 PostgreSQL statements that render.
Integration validation
Applied #2806–#2819 together on master (bdf8ac31), with the stacked PRs on top of their bases (#2806 → #2807 → #2808, #2806 → #2809 → #2810 and #2811 → #2812).
- Each branch merges cleanly into
master. Between the branches, conflicts are limited to adjacent additions (README/index rows, usage sections, imports, visitor and feature lists, one enum line and one alias guard).
- The integrated build passes Java 17 offline Gradle
spotlessApply check: 11,494 tests, 11,469 passed, 25 skipped, zero failures/errors. The grammar choice conflict check passes.
- On a corpus of 635 MySQL 8.4 and PostgreSQL 18 DDL/DCL statements, each accepted by the server, the integrated build parses 265 of 271 MySQL statements (
master: 206) and 363 of 364 PostgreSQL statements (master: 328). Every MySQL 8.4 non-reserved word and PostgreSQL 18 unreserved or column-name keyword parses as a column and table name.
- On paired MySQL 8.4 and PostgreSQL 18.3 servers, all 263 MySQL and 362 PostgreSQL statements rendered by the integrated build give the same results as the originals.
Sorry, something went wrong.
Uh oh!
There was an error while loading. Please reload this page.
CREATE USER and DEFINER read user@host with their own copies of the
same rule. Neither accepted app@'%' or 'app'@localhost, because the
lexer reads app@ and @localhost as single tokens. Without a dialect a
double-quoted part also lost its quotes, so CREATE USER "app"@"%"
rendered as app@%.
Add one MySqlAccountName() production that splits those tokens, keep
the quote character of double-quoted and backquoted parts apart from
their value, and use it for CREATE USER and DEFINER.
Signed-off-by: minleejae <[email protected]>
This was referenced Oct 14, 2026
Uh oh!
There was an error while loading. Please reload this page.
Sorry, something went wrong.
Uh oh!
There was an error while loading. Please reload this page.
Uh oh!
There was an error while loading. Please reload this page.
Assignees
No one assigned
Milestone
No milestone
Development
Successfully merging this pull request may close these issues.
Uh oh!
There was an error while loading. Please reload this page.
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
|