-
Notifications
You must be signed in to change notification settings - Fork 94
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Support the full WordPress PHPUnit test suite #55
Comments
Looking for prior art on this I found an open-source Java-based SQL parser and translator: https://github.com/jOOQ/jOOQ I recorded 25k SQL queries during WordPress and WooCommerce setup, and pasted them on their demo page. Here's what's not supported:
Everything else worked, including many jOOQ could perhaps be ported to PHP, or at least be a good source of inspiration. |
See also: List of Converter Tools on sqlite.org SQLFairy seems interesting:
Edit: Actually, it's pretty limited:
|
Another idea: Simplify the sql_yacc.yy grammar definition shipped with MySQL to remove unsupported features (like polygons etc), autogenerate a tokenizer, then add SQLite translation layer. |
I recorded all SQL queries ran during the WordPress PHPUnit test suite run: @aristath found the open-source phpmyadmin/sql-parser project that tokenizes and parses MySQL queries. |
I built a proof of concept of translating CREATE TABLE queries to SQLite: https://gist.github.com/adamziel/d4d2f335a7671054d9ccee8d723ec0e8 It reproduces similar steps as this plugin. It translated all WordPress MySQL tables I gave it into SQLite-compatible queries – see the |
I expanded the above translator to https://gist.github.com/adamziel/7f71ddba7d240d5b6f342fa2d9c55ea3 Even though this version is quick, dirty, and makes a bunch of assumptions that won't always hold, it translates all the queries from the WordPress unit test suite into syntactically valid SQLite queries. It deals with date functions, intervals, It's still missing support for Support for |
The explorations continue in WordPress/sqlite-database-integration |
The lexer-based implementation in the
The remaining failures will have to be fixed in WordPress core. I recommend migrating to WordPress/sqlite-database-integration once the lexer-based implementation is merged. |
The new version of WordPress/sqlite-database-integration is now released: https://wordpress.org/plugins/sqlite-database-integration/ |
Migrates Playground from regexp-based [wp-sqlite-db](aaemnnosttv/wp-sqlite-db#55) to the official [sqlite-database-integration](https://github.com/WordPress/sqlite-database-integration) plugin which [translates queries using SQL parser](WordPress/sqlite-database-integration#9) instead of regular expressions. This makes for a more reliable SQLite integration that passes almost all WordPress unit tests. [Learn more](aaemnnosttv/wp-sqlite-db#55) about the problem with regular expressions.
Migrates Playground from regexp-based [wp-sqlite-db](aaemnnosttv/wp-sqlite-db#55) to the official [sqlite-database-integration](https://github.com/WordPress/sqlite-database-integration) plugin which [translates queries using SQL parser](WordPress/sqlite-database-integration#9) instead of regular expressions. This makes for a more reliable SQLite integration that passes almost all WordPress unit tests. [Learn more](aaemnnosttv/wp-sqlite-db#55) about the problem with regular expressions.
This issue has been solved in the WordPress/sqlite-database-integration plugin, which is available in WordPress Plugin Directory. I'll leave it open here for posterity.
The problem
A lot of WordPress unit tests fail with the SQLite plugin is installed.
The root cause is the method of rewriting MySQL queries to SQLite queries: regular expressions and string lookups. It's hard to support the variety of SQL queries used in WordPress using these tools. I explored patching this plugin in WordPress Playground, but there's too many cases to cover – I included a few examples of failing queries at the bottom of this description.
Proposed solution
Parsing MySQL queries and using contextual information would make this plugin much more bulletproof.
Some queries are hard to reason about with tools like
preg_replace
orstrpos
:In contrast, applying the SQL grammar would make rewriting these queries much easier:
How to parse SQL queries?
Full parsing may not be needed. Even the array representation from the examples above may be too much. Creating many objects, arrays, and function calls for each SQL query would make WordPress extremely slow. There's a faster alternative.
Consider WP_HTML_Tag_Processor, a new WordPress API that enables adding, removing, and updating HTML attributes. It never turns the input HTML into a tree. Instead, it consumes the input HTML string one tag and one attribute at a time, and uses the contextual information to build the output HTML:
Perhaps the same technique could be used to rewrite MySQL queries?
For example:
Too low-level? Here's a higher-level idea:
Use
preg_match
to capture the next token, but nothing else. The parser would still move forward a single token at a time and make decisions based on what it just captured. The idea is to never write a regexp for the entire query. It's more readable than the lower-level counterparts, still reasonably fast, and only treats one token at a time. Also – if it works, it could be replaced by a lower-level implementation relatively easily.While I am proposing a major change, I specifically don't mean a full rewrite. This plugin got a lot of things right:
The existing work is an excellent foundation and I only propose to take it to the next level.
Finally, thank you for maintaining this plugin @aaemnnosttv! It made WordPress Playground possible.
Failing queries
Here's a few examples of queries that didn't work for me at one point or another:
cc @aristath @felixarntz @dmsnell @gziolo
The text was updated successfully, but these errors were encountered: