我正在尝试使用COPY语句转储PostgreSQL表。我正在使用COPY而不是pg_dump,因为我需要在其中一个列上执行转换。
我想要执行的语句基本上是这个
COPY ( SELECT 'punt' ) TO PROGRAM '7z a -si C:/Users/Public/Documents/punt';
但我收到了一般错误
ERROR: program "7z a -si C:/Users/Public/Documents/punt" failed
DETAIL: child process exited with exit code 1
我正在尝试通过类似于COPY
文档中的the fourth example的7zip传递COPY
输出,以便压缩输出,因为数据库大约是130 GB而我是'理想情况下使用SSD。以下命令工作正常:
COPY ( SELECT 'punt' ) TO 'C:/Users/Public/Documents/punt';
结果为COPY 1
。我在psql提示符下执行了以下命令,它也有效,这使我对语法和权限相当自信:
\! echo 'punt' | 7z a -si C:/Users/Public/Documents/punt
我是否遗漏了有关cmd
管道或7zip可执行权限的内容?
编辑: Postgres版本为9.3.3
根据Craig Ringer的回答,将dir权限更改为NETWORK SERVICE
后,我仍然遇到同样的错误。但是,这并没有解决问题并且错误是相同的。即使在更改了目标目录的权限以完全控制Everyone
之后,我仍然遇到了同样的错误。我也尝试更改7zip可执行文件和7zip Program Files
目录的权限无效。
在实验中,我运行了以下内容,将副本中的输入从等式中取出:
COPY ( select '1' ) TO PROGRAM 'echo punt | 7z a -si C:/Users/Public/Documents/punt';
并且奇怪地得到了失败消息,但是退出代码为255,对于7zip has the meaning"用户停止了进程"。我自己似乎无法找到理由。
答案 0 :(得分:3)
这是一个权限问题。
默认情况下,PostgreSQL服务器为9.2及以上版本的NETWORKSERVICE
或9.1及以下版本的用户postgres
运行。 COPY
以自己运行的用户PostgreSQL运行服务器端。
这些都不可能有权写入C:\Users\Public\Documents
。
您需要授予PostgreSQL服务用户使用Windows安全属性对话框写入的权限,或者选择其可以写入的其他位置。
它与\!
一起使用,因为psql
作为您的用户运行,将有权在那里写入,而\!
运行命令客户端当用户正在运行psql
。
答案 1 :(得分:2)
在我的编辑中删除7zip位,255错误代码实际上来自cmd
未找到7zip exe。我把7zip.exe
放在C:/上(无法弄清楚在程序文件中转义空间)并运行
COPY ( SELECT 'punt' ) TO PROGRAM 'C:/7z a -si C:/Users/Public/Documents/punt';
和这有效。我猜测NETWORKSERVICE
用户没有加载path
环境变量,但我不确定。
我将C:/Users/Public/Documents
上的权限设置为默认值,而COPY ... TO PROGRAM
仍然有用,因此此特定情况下文件权限不是问题。如果我再次遇到这样的问题,我仍然会先看看Craig Ringer的建议。
答案 2 :(得分:1)
CMD
无法识别带空格的路径。 COPY FROM PROGRAM
无权访问PATH
变量。只需将您的PROGRAM_NAME像RESOURCE_NAME一样用双撇号括起来,即可完成:
COPY ( SELECT 'punt' ) TO PROGRAM '"C:/Program Files/bla/bla/7z.exe" a -si "C:/Users/Public/Documents/punt"';