Как исключить дубликаты записей при добавлении CSV файла в таблицу БД
Таблица выглядит таким образом:
Категория по буквам |Категория по аббревиатуре|Дата |П_1 |П_2
____________________|_________________________|__________|________|________|
Буквенная |ZZZ |07.20.2020|2 |3
______________|_________________________|__________|________|________|
Численная |ZZZ |07.20.2020|1 |1
______________|_________________________|__________|________|________|
Численная |AAA |07.20.2020|3 |7
______________|_________________________|__________|________|_________
Буквенная |CCC |07.20.2020|40 |1
______________|_________________________|__________|________|_________
Буквенная |CCC |07.24.2020|0 |0
Нужно чтобы блок данных загружался в таблицу БД после проверки, что еще нет данных за сформированную дату (дубликаты данных), иначе выводится уведомление, что данные с такой датой уже существуют в БД.
Данные загружаются таким образом:
import urllib
from sqlalchemy import create_engine
import pyodbc
params = urllib.parse.quote_plus("DRIVER={SQL Server Native Client 11.0};SERVER=dagger;DATABASE=test;UID=user;PWD=password")
engine = create_engine("mssql+pyodbc:///?odbc_connect=%s" % params)
df.to_sql("mytable", engine, index=False, if_exists="append")
Ответы (1 шт):
Автор решения: MaxU
→ Ссылка
Я вижу два варианта решения:
- заливать данные из DataFrame во временную таблицу и потом делать вставку с проверкой на стороне SQL Server.
- вычитываем всю таблицу из SQL Server в DataFrame, получаем новый DataFrame с записями, которые отстутствуют в таблице SQL Server, заливаем данные обратно в таблицу.
Второй подход может быть очень медленным и со временем таблица может стать настолько большой, что она не поместится в памяти в виде DataFrame. Поэтому я бы выбрал первый вариант.
Решение:
import urllib
params = urllib.parse.quote_plus("DRIVER={SQL Server Native Client 11.0};SERVER=dagger;DATABASE=test;UID=user;PWD=password")
engine = create_engine("mssql+pyodbc:///?odbc_connect=%s" % params)
# вставляем данные во временную таблицу
df.to_sql("tmp_table", index=False, if_exists="replace")
# подготавливаем SQL для вставки уникальных записей
qry = """
INSERT INTO target_table (col1, col2, col3)
SELECT * FROM tmp_table tmp
WHERE NOT EXISTS (
SELECT 1
FROM target_table tgt
WHERE tgt.col1 = tmp.col1 AND tgt.col2 = tmp.col2 ...
)
"""
con = engine.connect()
cur = con.cursor()
cur.execute(qry)
con.commit()