pg_restore: 错误: 无法从输入文件读取: 文件结束

我试图创建一个存储在我的数据库中的表的转储。 这个表叫做
webapp_product
为了创建转储文件,我使用以下命令:
docker-compose exec db1 pg_dump -F tar -d db -U user -t webapp_product > /home/backup.tar  

然后,在另一台机器上:

sudo mv backup.tar ../pgdata
docker-compose exec db1 sh
pg_restore -Ft -C -U user -d db /var/lib/postgresql/data/pgdata/backup.tar
很不幸,它总是以相同的情况结束。我确实收到以下错误日志:
pg_restore: error: could not read from input file: end of file
我还尝试了另一种方法。在移动备份文件之后,我一直在尝试使用:
cat /var/lib/postgresql/data/pgdata/backup.sql | psql -d db -U user
在调用该命令后,我一直收到一个错误,说我无法创建重复项(记录的ID相同)。 为了继续进行,我尝试关闭所有约束,但没有产生预期的效果。 @更新1 backup.tar文件包含以下行:
-- NOTE:
--
-- File paths need to be edited. Search for $$PATH$$ and
-- replace it with the path to the directory containing
-- the extracted data files.
--
--
-- PostgreSQL database dump
--

-- Dumped from database version 12.1 (Debian 12.1-1.pgdg100+1)
-- Dumped by pg_dump version 12.1 (Debian 12.1-1.pgdg100+1)

它能影响数据恢复的过程吗?

并且有以下结尾:



--
-- PostgreSQL database dump complete
--



我一直收到一个错误提示,说我无法创建重复项(记录的ID相同)。你试图加载数据覆盖现有数据。当你尝试这样做时,你希望发生什么?现有数据应该被删除吗? - jjanes
你展示的tar文件的前导行并不是真正的tar文件的样子。如果你在它上面执行tar -tf backup.tar会发生什么? - jjanes
@jjanes 使用以下命令的结果: tar -tf backup.tar. toc.dat.
tar: 跳至下一个头文件。
tar: 390 处有单独的零块。 tar: 由于先前的错误,以失败状态退出。
- D Komo
@jjanes 基本上,我只是想更新存储在第二个服务器上的一个表的记录。 - D Komo
2个回答

你真的有两个问题。首先,你有一个损坏的tar文件。我会把这归咎于你使用docker。如果在移动文件之前在docker端运行tar -tf ...,它是否也被损坏了? 其次,你不想恢复数据,而是想合并它。pg_dump/pg_restore不能做到这一点。你需要弄清楚你想要做什么(覆盖、聚合、分配新的主键并将其插入为新行),然后实施它。你可能想使用COPY\copy将数据从第一个系统中取出,以便第二个系统可以看到它。之后,你可以自由决定如何处理这些数据。你可以使用Python、Perl或SQL(在\copy到临时表之后)或者你最喜欢的工具来实现合并。

@jjanes是对的。 Docker导致了错误。 Docker导致了错误。我使用Docker创建的文件损坏了。一旦我直接从Docker中导出它,使用shell和运行命令:
tar -tf backup.tar

该文件已被定义为有效文件。

此外,@jjanes 也正确指出了第二种情况。使用 pg_dump 是毫无意义的。 在我的情况下,最好的解决方案是使用 Django 的内置函数:

dumpdata
loaddata
它运行得非常好!