以下内容完全是一个数据库小白的经验之谈,可能不太准确,见谅!
最近两天试图在树莓派上部署一个web应用,具体目标就是将接收到的数据转存到数据库中,一个是本地的kudu数据库,另一个是mysql数据库
# 如kudu库
impala.create_update_data('main', kudu_engine, df_main, 'main')
impala.create_update_data('child', kudu_engine, df_child, 'child')
impala.create_update_data('info', kudu_engine, df_info, 'info')
# 如mysql库
mysql.create_update_data('main', mysql_engine, df_main, 'main')
mysql.create_update_data('child', mysql_engine, df_child, 'child')
mysql.create_update_data('info', mysql_engine, df_info, 'info')
# impala
with engine.begin() as conn:
conn.execute("UPSERT INTO {} ({}) VALUES ({})".format(table, keys, values))
# mysql
with engine.begin() as conn:
conn.execute("REPLACE INTO {} ({}) VALUES ({})".format(table, keys, values))
但发现一个令人抓狂的问题:在本地x86机器上完全没问题,相同代码在树莓派上就完全看运气了(某些请求能正常入库,而大部分无法入库,而且没有任何异常)
最开始怀疑是因为机器性能导致,但尝试把导入kudu库的功能去掉后,发现入mysql库没有问题,所以是导入kudu库的代码问题。
将impala的‘with engine.begin() as conn:’换成:
conn = engine.connect()
conn.execute("UPSERT INTO {} ({}) VALUES ({})".format(table, keys, values))
conn.close()
发现一切又恢复正常了
看来是‘with engine.begin() as conn:’这条语句导致的
查了一下,上面这条语句好像是为了使用事物,但什么是事物,还需要进一步学习,最终把所有的‘with engine.begin() as conn:’改成‘with engine.connect() as conn:’,正常了!
总而言之,这里总结出的经验就是别用with engine.begin() as conn
参考:https://docs.sqlalchemy.org/en/13/core/connections.html
2020-04-30更新
在进行上面的修改后,又发现问题:树莓派中使用impala engine的df.to_sql(table, engine, if_exists=‘append’)会出问题,而mysql engine的貌似没有问题,所以索性把所有df.to_sql全部进行替换
dic = df.to_dict('records')
keys = ', '.join(
key for key, value in dic[0].items()
)
values = ''
for item in dic:
value = '(' + ', '.join(
"'{}'".format(value) \
if type(value) == str else "{}".format(value) \
for key, value in item.items()
) + ')'
values = (values + ',' + value).strip(',')
with engine.connect() as conn:
conn.execute("INSERT INTO {} ({}) VALUES ({})".format(table, keys, values))