Skip to content

Generate MySQL REPLACE statements for replacement prefixes - #69

Open
ac1982 wants to merge 1 commit into
wireservice:masterfrom
ac1982:fix/mysql-replace-inserts
Open

ac1982 wants to merge 1 commit into
wireservice:masterfrom
ac1982:fix/mysql-replace-inserts

Conversation

@ac1982

@ac1982 ac1982 commented Oct 14, 2026

Copy link
Copy Markdown

MySQL REPLACE is a statement, not an INSERT modifier. csvsql --prefix REPLACE --insert currently emits INSERT REPLACE INTO ... and fails with MySQL error 1064.

Use a separate SQLAlchemy Insert subclass for MySQL replacement writes. Its dialect compiler retains SQLAlchemy's column quoting and bound parameters while changing the leading keyword to REPLACE. Other modifiers, ordinary inserts, chunking, and SQLite's OR REPLACE keep their existing paths; the caller's prefix list is not modified.

Fixes #44.

Validation:

  • Full agate-sql suite on SQLAlchemy 1.4.54 and 2.1.4: 20 passed, 8 subtests passed. Six new replacement cases fail on the base revision.
  • Real MySQL 8.4.11 on both SQLAlchemy versions: ordinary/chunked replacements, LOW_PRIORITY, unchanged INSERT IGNORE, bound values containing INSERT REPLACE, and caller-controlled rollback pass.
  • Actual csvsql command reproduces error 1064 before the fix and persists the expected replacement rows afterwards. csvsql tests: 22 passed, 1 skipped, 10 subtests passed.
  • flake8, isort, check-manifest, and Sphinx documentation build pass.

Local validation used Linux/Python 3.12. The full OS/Python CI matrix was not run. This change leaves transaction ownership unchanged: csvsql starts and commits its own transaction; the separate owned-connection issue in #68 is independent.

AI-assisted implementation and validation.

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.

MySQL needs REPLACE and not INSERT OR REPLACE (though it does use INSERT IGNORE)

1 participant