pypika
pypika copied to clipboard
SQLite Insert or Ignore
While looking into https://github.com/tortoise/tortoise-orm/issues/527 I came upon the question of where there is any way to do the SQLLite query
INSERT OR IGNORE INTO "foo" VALUES (1, 'm')
it seems like the SQLLiteQueryBuilder insert_or_replace is very similar to what is needed. In copying insert_or_replace
it depends on the QueryBuilder's replace_sql method . Using this pattern I propose to add a insert_or_ignore
method to the SQLLiteQueryBuilder like so
class SQLLiteQueryBuilder(QueryBuilder):
QUERY_CLS = SQLLiteQuery
def __init__(self, **kwargs: Any) -> None:
# ... all the same just concatenating the below line
self._insert_or_ignore = False
@builder
def insert_or_ignore(self, *terms: Any) -> "SQLLiteQueryBuilder":
self._apply_terms(*terms)
self._ignore = True # not sure if this is good to change, seems like it's used elsewhere so maybe not this line
self._insert_or_ignore = True
def _ignore_sql(self, **kwargs: Any) -> str:
prefix = "INSERT OR " if self._insert_or_ignore else ""
return prefix + super()._ignore_sql(**kwargs)
and then the additional changes to the base QueryBuilder like so
class QueryBuilder(Selectable, Term):
# ...maybe somewhere close to the `def _replace_sql` I don't know
def _ignore_sql(self, **kwargs: Any) -> str:
return "IGNORE INTO {table}".format(
table=self._insert_table.get_sql(**kwargs),
)
this would then allow an interaction like so
from pypika import SQLLiteQuery
SQLLiteQuery.into("foo").insert_or_ignore(1, 'm')
and render out to
INSERT OR IGNORE INTO "foo" VALUES (1, 'm')
maybe this is already possible via other mechanisms, pypika is pretty sweet already so please correct me if I'm wrong.
considerations
seems like going this way is kind of wrong. Would it make more sense to override the .ignore
method so that it could look like
SQLLiteQuery.into("foo").insert(1, 'm').ignore()
btw this call currently works but I don't think what it outputs is valid SQLLite syntax
INSERT IGNORE INTO "foo" VALUES (1, 'm')
I think SQLLiteQuery.ignore()
should output INSERT OR IGNORE
. I just started using PyPika and immediately ran into this issue, it would be really nice to get it fixed. Thanks!