{"id":5504,"library":"sqloxide","title":"Sqloxide","description":"Sqloxide provides Python bindings for the high-performance `sqlparser-rs` Rust library. It enables fast, efficient, and accurate parsing of SQL queries into a structured Abstract Syntax Tree (AST) in Python, making it suitable for tasks like building data lineage graphs, especially across complex or auto-generated SQL codebases that include deeply nested queries, sub-selects, and table aliases. The library is currently at version 0.61.1 and its minor version now tracks the underlying `sqlparser-rs` library's minor version, indicating a responsive release cadence.","status":"active","version":"0.61.1","language":"python","source_language":"en","source_url":"https://github.com/wseaton/sqloxide","tags":["SQL","parser","AST","Rust","data lineage"],"install":[{"cmd":"pip install sqloxide","lang":"bash","label":"Install stable release"}],"dependencies":[],"imports":[{"symbol":"parse_sql","correct":"from sqloxide import parse_sql"},{"note":"Used for programmatic modification of the SQL AST.","symbol":"mutate_expressions","correct":"from sqloxide import mutate_expressions"},{"note":"Used for programmatic modification of the SQL AST, specifically relations.","symbol":"mutate_relations","correct":"from sqloxide import mutate_relations"}],"quickstart":{"code":"from sqloxide import parse_sql\n\nsql_query = \"\"\"\nSELECT\n    employee.first_name,\n    employee.last_name,\n    call.start_time,\n    call.end_time,\n    call_outcome.outcome_text\nFROM\n    employee\nINNER JOIN call ON call.employee_id = employee.id\nINNER JOIN call_outcome ON call.call_outcome_id = call_outcome.id\nORDER BY\n    call.start_time ASC;\n\"\"\"\n\n# Parse the SQL query, specifying a dialect (e.g., 'ansi')\nast_output = parse_sql(sql=sql_query, dialect='ansi')\n\n# The output is a Python object representing the AST\n# print(ast_output) # Uncomment to see the full AST\n\n# Example of accessing parts of the AST (structure depends on SQL and sqlparser-rs version)\nif ast_output and isinstance(ast_output, list) and 'Query' in ast_output[0]:\n    query_body = ast_output[0]['Query']['body']\n    if 'Select' in query_body:\n        projection_items = query_body['Select']['projection']\n        print(f\"Number of projected columns: {len(projection_items)}\")\n        print(f\"First projected item: {projection_items[0]}\")","lang":"python","description":"This quickstart demonstrates how to parse a SQL query using `sqloxide.parse_sql`. The function returns a Python object which is a typed Abstract Syntax Tree (AST) that mirrors the `sqlparser-rs` AST schema. You can specify different SQL dialects (e.g., 'ansi', 'mysql', 'postgres', 'sqlite', 'snowflake', 'bigquery', 'hive', 'generic') for accurate parsing."},"warnings":[{"fix":"Upgrade your Python environment to 3.9 or higher.","message":"Sqloxide v0.61.0 dropped support for Python 3.7 and 3.8, requiring Python 3.9 or newer. This change was due to incompatibilities with `pyo3` 0.28, which was upgraded alongside `sqlparser-rs` to 0.61.0.","severity":"breaking","affected_versions":">=0.61.0"},{"fix":"If your code relies on directly inspecting or manipulating the AST structure for these statement types, you will need to update your logic to match the new JSON/Python object shape. Refer to the `sqlparser-rs` 0.57-0.61 release notes for specific structural changes.","message":"With the upgrade to `sqlparser-rs` 0.61.0 in sqloxide v0.61.0, several `Statement` variants (e.g., `Update`, `CreateView`, `Truncate`, `Grant`, `Revoke`) changed their internal representation from inline struct variants to tuple-struct wrappers. This significantly alters the `serde`/JSON shape of the AST for these statement types compared to versions prior to 0.61.0.","severity":"breaking","affected_versions":">=0.61.0"},{"fix":"Be aware that minor version bumps in sqloxide may now correspond to significant updates and potential breaking changes in the underlying `sqlparser-rs` library. Review `sqlparser-rs` changelogs in addition to sqloxide's for detailed impact analysis during upgrades.","message":"Starting with v0.61.0, sqloxide adopted a new versioning scheme where its minor version (e.g., `0.61.x`) now tracks the minor version of the wrapped `sqlparser-rs` crate (e.g., `0.61`). This means that `sqloxide`'s version number will change more frequently and directly reflect the underlying Rust parser's evolution.","severity":"gotcha","affected_versions":">=0.61.0"},{"fix":"Upgrade to sqloxide v0.61.1 or later to ensure proper exception propagation from mutation callbacks. If on an older version, add robust error checking within and around your mutation callbacks.","message":"In versions prior to v0.61.1, exceptions raised within Python callbacks provided to `mutate_relations` or `mutate_expressions` functions might not have been properly propagated. This could lead to silently returning partially mutated results instead of signalling an error.","severity":"gotcha","affected_versions":"<0.61.1"}],"env_vars":null,"search_vec":"'0.61.1':71 'abstract':29 'accur':21 'across':46 'alias':64 'ast':32,94 'auto':50 'auto-gener':49 'bind':5 'build':41 'cadenc':91 'codebas':53 'complex':47 'current':68 'data':42,96 'deepli':56 'effici':19 'enabl':17 'especi':45 'fast':18 'generat':51 'graph':44 'high':9 'high-perform':8 'includ':55 'indic':87 'librari':15,66,83 'like':40 'lineag':43,97 'make':35 'minor':74,85 'nest':57 'pars':22 'parser':93 'perform':10 'provid':3 'python':4,34 'queri':25,58 'releas':90 'respons':89 'rs':13,82 'rust':14,95 'select':61 'sql':24,52,92 'sqloxid':1,2 'sqlparser':12,81 'sqlparser-r':11,80 'structur':28 'sub':60 'sub-select':59 'suitabl':37 'syntax':30 'tabl':63 'task':39 'track':77 'tree':31 'under':79 'version':70,75,86","created_at":"2026-04-14T01:36:42.062749+00:00","updated_at":"2026-04-17T14:06:12.721989+00:00","problems":[{"fix":"pip install sqloxide","cause":"The `sqloxide` library is not installed in your current Python environment.","error":"ModuleNotFoundError: No module named 'sqloxide'"},{"fix":"import sqloxide\nast = sqloxide.parse_sql_to_ast(\"SELECT 1 FROM my_table\")","cause":"The `parse_sql_to_ast` function was called without providing the necessary SQL query string argument.","error":"TypeError: parse_sql_to_ast() missing 1 required positional argument: 'sql'"},{"fix":"Review and correct the SQL query string to ensure it is valid, for example: `sqloxide.parse_sql_to_ast(\"SELECT column_name FROM my_table\")`","cause":"The provided SQL query string is syntactically incorrect or contains elements not supported by the underlying `sqlparser-rs` library.","error":"sqloxide.SqloxideError: ParserError(\"Expected an expression after SELECT, found: FROM\")"},{"fix":"Iterate through the returned list or access elements by index, and then access dictionary keys using `['key']` notation. For example:\n\nimport sqloxide\nast = sqloxide.parse_sql_to_ast(\"SELECT 1; SELECT 2;\")\nfor statement_dict in ast:\n    print(statement_dict.keys())\n\n# Or for a single statement:\nsingle_statement_ast = sqloxide.parse_sql_to_ast(\"SELECT 1\")\nfirst_statement = single_statement_ast[0]\nprint(first_statement.get('Select'))","cause":"The `parse_sql_to_ast` function returns a list of dictionaries (representing SQL statements), but you are attempting to access an attribute directly on this list object as if it were a single custom object or dictionary.","error":"AttributeError: 'list' object has no attribute 'statements'"}],"ecosystem":"pypi","meta_description":null,"install_score":null,"quickstart_score":null,"quickstart_tag":null,"pypi_latest":"0.61.1","cli_name":"","cli_version":null,"type":"library","homepage":null,"github":"https://github.com/wseaton/sqloxide","docs":null,"changelog":null,"pypi":"https://pypi.org/project/sqloxide/","npm":null,"openapi_spec":null,"status_page":null,"smithery":null,"categories":["database","data"],"base_url":null,"auth_type":null,"provenance":{"verified_status":"passing","verified_at":"2026-06-28","last_verified":"2026-08-30","next_check":"2026-07-28","install_tag":null}}