查找光盘上缺少文件的PostgreSQL记录以及光盘上缺少数据库记录的文件

时间:2019-02-19 12:14:12

标签: sql postgresql postgresql-9.6

我正在使用PostgreSQL 9.6只读副本,无法在其中创建函数或临时表。

在一个表中有一个应该在光盘上的文件列表。在完全不同的服务的目录中,有文件本身,以file_id命名。

  Column   |   Type
-----------+-----------
 file_id   |  integer
 name      |  text

在另一台计算机上的光盘上

ls -rt /var/www/dbfiles
519288     519290     519297     519298     519231     ...

大约有5000条记录和大约5000个文件,但我有理由相信它们不匹配。因此,我正在尝试找到一种运行查询的方法,该查询将显示数据库中的哪些记录在磁盘上没有文件,而磁盘上的哪些文件在数据库中没有记录。现在是一次性的,所以我不介意手动修改目录列表。

如果我可以将目录列表导入到表中,则只需进行外部联接并在每侧查找空值。有没有一种方法可以对充满ID的子查询进行外部联接?像

SELECT f.name, dir_listing.id FROM files f
FULL OUTER JOIN (SELECT (519288, 519290, 519297, 519298, 519231...) AS id) AS dir_listing

输出看起来像

 name          |   id
---------------+---------
 myfile.txt    | 519288
 otherfile.txt | 
               | 519290 

(等)

从CSV和VLOOKUP中救救我!

2 个答案:

答案 0 :(得分:1)

您可以使用VALUES()

SELECT f.name, dir_listing.id
FROM files f FULL OUTER JOIN
     (VALUES (519288), (519290), (519297), (519298), (519231), 
     ) AS dir_listing (id)
     ON f.file_id = dir_listing.id;

答案 1 :(得分:1)

您的想法有效,您使用的语法错误。

此表达式:

F9

返回具有单列的单行,这是具有许多字段的匿名记录。

您可以做的是在values子句中列出ID(如INSERT语句所示):

SELECT (519288, 519290, 519297, 519298, 519231...)

请注意,每个值都用括号括起来,在每个值的行上创建。

如果您希望少键入一些内容,则可以使用未嵌套的数组常量:

SELECT f.name, dir_listing.id 
FROM files f
  FULL OUTER JOIN (
    values (519288), (519290), (519297), (519298), (519231), (...)
  ) AS dir_listing(id) on f.id = dir_listing.id;