您好我正在尝试使用python将csv文件写入SQL Server数据库中的表。我传递参数时遇到错误,但手动操作时我没有遇到任何错误。这是我正在执行的代码。
cur=cnxn.cursor() # Get the cursor
csv_data = csv.reader(file(Samplefile.csv')) # Read the csv
for rows in csv_data: # Iterate through csv
cur.execute("INSERT INTO MyTable(Col1,Col2,Col3,Col4) VALUES (?,?,?,?)",rows)
cnxn.commit()
错误:pyodbc.DataError:('22001','[22001] [Microsoft] [ODBC SQL Server驱动程序] [SQL Server]字符串或二进制数据将被截断。(8152)(SQLExecDirectW )[01000] [Microsoft] [ODBC SQL Server驱动程序] [SQL Server]语句已终止。(3621)')
但是,当我手动插入值时。它工作正常
cur.execute("INSERT INTO MyTable(Col1,Col2,Col3,Col4) VALUES (?,?,?,?)",'A','B','C','D')
我确保数据库中存在TABLE,数据类型与我传递的数据一致。连接和光标也正确。行的数据类型是“list”
答案 0 :(得分:28)
考虑动态构建查询以确保占位符数与表和CSV文件格式匹配。然后,只需确保您的表格和CSV文件正确无误,而不是检查您是否在代码中键入了足够的?
占位符。
以下示例假设
test.csv
MyTable
...
with open ('test.csv', 'r') as f:
reader = csv.reader(f)
columns = next(reader)
query = 'insert into MyTable({0}) values ({1})'
query = query.format(','.join(columns), ','.join('?' * len(columns)))
cursor = connection.cursor()
for data in reader:
cursor.execute(query, data)
cursor.commit()
如果文件中未包含列名:
...
with open ('test.csv', 'r') as f:
reader = csv.reader(f)
data = next(reader)
query = 'insert into dbo.Test values ({0})'
query = query.format(','.join('?' * len(data)))
cursor = connection.cursor()
cursor.execute(query, data)
for data in reader:
cursor.execute(query, data)
cursor.commit()
答案 1 :(得分:0)
您可以将列作为参数传递。例如:
for rows in csv_data: # Iterate through csv
cur.execute("INSERT INTO MyTable(Col1,Col2,Col3,Col4) VALUES (?,?,?,?)", *rows)
答案 2 :(得分:0)
我把它整理好了。该错误是由于表的大小限制限制。它改变了列容量,例如从col1 varchar(10)到col1 varchar(35)等。现在它工作正常。
答案 3 :(得分:0)
我修改了Brian上面编写的代码,如下所示,因为上面发布的代码不适用于我要上传的定界文件。也可以忽略row.pop()
行,因为仅对于我尝试上传的文件集才需要。
def upload_table(path, filename, delim, cursor):
"""
Function to upload flat file to sqlserver
"""
tbl = filename.split('.')[0]
cnt = 0
with open (path + filename, 'r') as f:
reader = csv.reader(f, delimiter=delim)
for row in reader:
row.pop() # can be commented out
row = ['NULL' if val == '' else val for val in row]
row = [x.replace("'", "''") for x in row]
out = "'" + "', '".join(str(item) for item in row) + "'"
out = out.replace("'NULL'", 'NULL')
query = "INSERT INTO " + tbl + " VALUES (" + out + ")"
cursor.execute(query)
cnt = cnt + 1
if cnt % 10000 == 0:
cursor.commit()
cursor.commit()
print("Uploaded " + str(cnt) + " rows into table " + tbl + ".")
答案 4 :(得分:0)
如果您在气流中使用 MySqlHook,如果带有参数的 cursor.execute() 抛出 san 错误
<块引用>TypeError: 在字符串格式化期间并非所有参数都被转换
使用 %s
而不是 ?
with open('/usr/local/airflow/files/ifsc_details.csv','r') as csv_file:
csv_reader = csv.reader(csv_file)
columns = next(csv_reader)
query = '''insert into ifsc_details({0}) values({1});'''
query = query.format(','.join(columns), ','.join(['%s'] * len(columns)))
mysql = MySqlHook(mysql_conn_id='local_mysql')
conn = mysql.get_conn()
cursor = conn.cursor()
for data in csv_reader:
cursor.execute(query, data)
cursor.commit()
答案 5 :(得分:-1)
您还可以使用以下任一方法将数据导入SQL:
可在此网页上找到更多详细信息: https://docs.microsoft.com/en-us/sql/relational-databases/import-export/import-data-from-excel-to-sql?view=sql-server-2017