tortoise / tortoise-orm

Familiar asyncio ORM for python, built with relations in mind
https://tortoise.github.io
Apache License 2.0
4.68k stars 392 forks source link

Corrupt sql generated when bulk_create method is configured with on_conflict parameter #1568

Open zzl221000 opened 8 months ago

zzl221000 commented 8 months ago

Describe the bug

In the sqlite engine, configuring update_fields will configure on_conflict for self.insert_query and self.insert_query_all, resulting in duplicate on conflict fields.

'INSERT INTO "fileevent" ("id","tn","date","url","status","create_at") VALUES (?,?,?,?,?,?) ON CONFLICT ("id", "id") DO UPDATE SET "url"=EXCLUDED."url","url"=EXCLUDED."url"'

To Reproduce sqlite3 and use bulk api

Expected behavior

'INSERT INTO "fileevent" ("id","tn","date","url","status","create_at") VALUES (?,?,?,?,?,?) ON CONFLICT ("id") DO UPDATE SET "url"=EXCLUDED."url","url"=EXCLUDED."url"'

droserasprout commented 2 months ago

Reproducible on 0.21.6:

from tortoise import Tortoise, models, fields
import asyncio

class Meta(models.Model):
    key = fields.TextField(primary_key=True)
    value = fields.IntField()

async def main():
    await Tortoise.init(
        db_url='sqlite://:memory:',
        modules={'models': ['__main__']},
    )
    await Tortoise.generate_schemas()

    data = {'a': 1, 'b': 2, 'c': 3}

    await Meta.bulk_create(
        objects=(Meta(key=k, value=v) for k, v in data.items()),
        on_conflict=('key',),
        update_fields=('value',),
    )

asyncio.run(main())