首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >Python \将CSV复制到远程服务器

Python \将CSV复制到远程服务器
EN

Stack Overflow用户
提问于 2017-10-15 19:02:33
回答 1查看 1.5K关注 0票数 1

我正在尝试将带有python3.6的csv (它有一个头和引号字符)复制到远程postgres 10服务器上的一个表中。它是一个大型CSV (2.5M行,800 It ),虽然我以前将它导入数据文件,然后使用dataframe.to_sql,但这非常占用内存,所以我转而使用COPY。

将复制与psycopg2或sqlalchemy一起使用会很好,但远程服务器无法访问本地文件系统。

在终端中使用psql,我已经成功地运行了下面的查询来填充表。我认为在psycopg2或sqlalchemy中使用\copy是不可能的。

代码语言:javascript
运行
复制
\copy table (col1, col2) FROM file_location CSV HEADER QUOTE '"' NULL ''

但是,当我尝试像下面这样使用一行psql -c命令时,它不起作用,我得到了错误:

错误:复制引号必须是一个单字节字符.

代码语言:javascript
运行
复制
psql -U user -h ip -d db -w pw -c "\copy table (col1, col2) FROM file_location CSV HEADER QUOTE '"' NULL ''"

你能告诉我为什么会这样吗?

这条单行-c psql语句在python中使用子进程模块实现要比打开终端和执行命令要容易得多,我不知道该如何做。如果你能提出一个解决办法或不同的方法,那就太好了。

======根据安德鲁的建议,将引号字符转义到命令行中。但是,在像下面这样在python中实现它时,会出现一个新的错误:

/bin/sh:-c:第0行:寻找匹配的‘’时意外的EOF

/bin/sh:-c:第1行:语法错误:文件意外结束

代码语言:javascript
运行
复制
"\"\copy table (col1, col2) FROM file_location CSV HEADER QUOTE '\"' NULL ''\""
cmd = f'psql -U {user} -h {ip} -d {db} -w {pw} -c {copy_statement}'
subprocess.call(cmd, shell=True)
EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2017-10-16 15:19:53

如果你能避免的话,尽量不要使用shell=True。最好自己标记命令以帮助sh。

代码语言:javascript
运行
复制
subprocess.call(["psql", "-U", "{user}", "-h", "{ip}", "-d", "{db}", "-w", "{pw}", "-c", "{copy statement}"])

在本例中,复制语句可以逐字传递给psql,因为没有shell引用问题需要考虑。(对于python,请注意,仍然需要引用这段代码,因此字符串将保持原样)。

如果仍然希望使用shell=True,则必须转义python和shell的字符串文本。

代码语言:javascript
运行
复制
"\"\copy table (col1, col2) FROM file_location CSV HEADER QUOTE '\\\"' NULL ''\""

将在python中创建一个字符串,

代码语言:javascript
运行
复制
"\copy table (col1, col2) FROM file_location CSV HEADER QUOTE '\"' NULL ''\"

这就是我们发现我们首先需要在我们的外壳上!

编辑(从评论中澄清某些内容)

subprocess.call,当不使用shell=True时,需要一个可迭代的参数。

所以你可以

代码语言:javascript
运行
复制
psql_command = "\"\copy table (col1, col2) FROM file_location CSV HEADER QUOTE '\\\"' NULL ''\""
# user, hostname, password, dbname all defined elsewhere above.
command = ["psql",
    "-U", user,
    "-h", hostname,
    "-d", dbname,
    "-w", password,
    "-c", psql_command,
]

subprocess.call(command)

https://docs.python.org/2/library/subprocess.html#subprocess.callhttps://docs.python.org/3/library/subprocess.html#subprocess.call

额外编辑:-请注意,为了避免shell注入,您应该使用这里描述的方法。请参阅https://docs.python.org/2/library/subprocess.html#frequently-used-arguments的警告部分

票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/46758865

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档