Данные в таблицу заносятся дважды
Есть такой код, который берет данные с api и заносит их в бд. Если оставить как сейчас, то записанные данные в бд дублируются(при одном вызове функции run_schedule_reg). Когда удаляю все что связанно со вторым поток , данные не дублируются. Никак не пойму в чем тут проблема. В первом потоке я записываю данные в бд. Во втором их достаю из б.д.
import requests, time, datetime, json, schedule, sqlite3
from threading import Thread
conn = sqlite3.connect('parser.sqlite', check_same_thread = False)
url = 'http://127.0.0.1:8000/api/reg/'
def get_registers(date):
full_page = requests.get(url, auth=("admin","admin"))
pars=json.loads(full_page.content.decode('utf-8'))
a=sorted(pars, key=lambda pars: pars['time_visit'])
cursor = conn.cursor()
with conn:
cursor.execute("CREATE TABLE IF NOT EXISTS `register` (`time` STRING, `number_car` VARCHAR)")
for i in a:
if i['date_visit']==date:
number_car=i["number_car"]
time_visit=i["time_visit"]
cursor.execute("insert into register values (?, ?)", (time_visit, number_car))
conn.commit()
cursor.close()
def run_schedule_reg():
now = datetime.datetime.now()
date = now.strftime("%d-%m-%Y")
schedule.every(1).minutes.do(get_registers,date)
while True:
schedule.run_pending()
time.sleep(1)
def print_time_visit(time_now):
cursor = conn.cursor()
with conn:
cursor.execute("SELECT * FROM `register`")
rows = cursor.fetchall()
for row in rows:
index=2
time_db=row[0][:index] + row[0][index+1:]
time_now_to_int =time_now[:index] + time_now[:index]
if abs(int(time_db) - int(time_now_to_int) ) < 30:
print(row[0], row[1])
cursor.close()
def run_schedule_time():
now = datetime.datetime.now()
time_now = now.strftime("%H:%M")
schedule.every(5).minutes.do(print_time_visit,time_now)
while True:
schedule.run_pending()
time.sleep(1)
thread1 = Thread(target=run_schedule_reg).start()
thread2 = Thread(target=run_schedule_time).start()
Ответы (1 шт):
У вас два треда выполняют задачи из одной очереди. Скорее всего при schedule.run_pending() задачи копируются и второй тред успевает их увидеть до того как первый снимит их с очереди
Второй тред убери, а таймер добавь в первый
Вот эта часть должна быть только один раз
while True:
schedule.run_pending()
time.sleep(1)
Сам код в таком виде.
import requests, time, datetime, json, schedule, sqlite3
from threading import Thread
conn = sqlite3.connect('parser.sqlite', check_same_thread = False)
url = 'http://127.0.0.1:8000/api/reg/'
def get_registers(date):
full_page = requests.get(url, auth=("admin","admin"))
pars=json.loads(full_page.content.decode('utf-8'))
a=sorted(pars, key=lambda pars: pars['time_visit'])
cursor = conn.cursor()
with conn:
cursor.execute("CREATE TABLE IF NOT EXISTS `register` (`time` STRING, `number_car` VARCHAR)")
for i in a:
if i['date_visit']==date:
number_car=i["number_car"]
time_visit=i["time_visit"]
cursor.execute("insert into register values (?, ?)", (time_visit, number_car))
conn.commit()
cursor.close()
def run_schedule_reg():
now = datetime.datetime.now()
time_now = now.strftime("%H:%M")
schedule.every(5).minutes.do(print_time_visit,time_now) # перенесем сюда
now = datetime.datetime.now()
date = now.strftime("%d-%m-%Y")
schedule.every(1).minutes.do(get_registers,date)
while True:
schedule.run_pending()
time.sleep(1)
def print_time_visit(time_now):
cursor = conn.cursor()
with conn:
cursor.execute("SELECT * FROM `register`")
rows = cursor.fetchall()
for row in rows:
index=2
time_db=row[0][:index] + row[0][index+1:]
time_now_to_int =time_now[:index] + time_now[:index]
if abs(int(time_db) - int(time_now_to_int) ) < 30:
print(row[0], row[1])
cursor.close()
thread1 = Thread(target=run_schedule_reg).start()
# убрать thread2 = Thread(target=run_schedule_time).start()
Ещё тут момент time_now = now.strftime("%H:%M") нужно перенести в функцию если нужно время исполнения