如何使用WP-CLI或其他自动过程批量删除所有未连接的图像?

时间:2017-04-07 作者:user658182

在使用WPML Media(一种为每种语言创建每个图像副本的插件)之后,我们现在有将近100000个重复图像,我们不打算使用这些图像,需要消除它们。

我们不仅需要从文件系统本身删除这些引用,还需要确保删除数据库中的所有引用,就像通过媒体库手动删除它们时通常发生的情况一样。

如果可能的话,我正在寻找WP-CLI解决方案。此解决方案非常有用,但它可以处理所有图像,而不仅仅是系统中未连接/未使用的图像。

How can I bulk delete media and attachments using WP-CLI?

给出了另一个解决方案,OP在评论中说,他最终用SQL实现了他的解决方案。

How do I delete thousands of unattached images?

我对命令行或mysql并不陌生,但对WP表不太熟悉,无法创建查询来维护数据库的完整性。如果是的话,那么请建议一个纯数据库相关的解决方案,或者PHP脚本,它将挂接到系统中,并以“wordpress”的方式进行操作。

我不是在寻找基于插件的解决方案。我尝试过DNUI、DX删除连接的媒体,还有许多其他方法,结果都很糟糕。

更新:使用“parent=0”来确定是否附加了图像是一个非常聪明的解决方案,我将其标记为答案。

有一种方法可以合法地在帖子中使用图像,并且父级仍然等于0;此时,您可以访问媒体库中的图像详细信息,并复制完整的图像源URL以手动粘贴到帖子中。The accepted answer\'s solution will delete these as well. 因此,我也要鼓励其他将这一点考虑在内的解决办法。

这可能需要扫描数据库以查找映像名称的实例,可能类似于wp cli search replace将使用的算法?

3 个回复
最合适的回答,由SO网友:birgire 整理而成

您可以尝试对通过@something链接到的答案进行此(未测试)修改

wp post delete $(wp post list --post_type=\'attachment\' --format=ids --post_parent=0)
删除附件的步骤without parents.

以给定的mime type, e、 g。image/jpeg 尝试:

wp post delete $(wp post list --post_type=\'attachment\' \\
    --format=ids --post_parent=0 --post_mime_type=\'image/jpeg\')
Notes:

测试前请记住先备份!

未附加的图像可能仍用于帖子内容或小部件中。

SO网友:Bart Dabek

接受的答案不会删除父级已不存在的附件的未连接媒体。。。通过db或其他未将连接的媒体父级标记为0的进程删除父级时,可能会发生这种情况。

下面是一个执行该检查的cli命令。

wp post delete $(wp db query  --skip-column-names --batch "select DISTINCT p1.ID  from wp_posts p1
left join wp_posts p2 ON p1.post_parent = p2.ID
where p1.post_type = \'attachment\'
AND p2.ID is NULL") --force

SO网友:jadkik94

我也遇到过类似的问题,但它涉及到占用空间而不在数据库中的图像(一些上传中断/崩溃,或wp post delete混乱,或从备份中恢复)。在这个问题和that one.

我最终使用了一种基于其他两个答案变化的解决方案:

# List all attachment URLs,
#  ... remove the host part and replace by regex fragment "^\\./" (first sed),
#  ... replace extension by empty string to match WP resizes (second sed)
#  ... and write list on terminal and in /tmp/files.txt
#  ... and see them in the less pager in case there\'s a lot of output
wp post list --post_type=\'attachment\' --field=guid 2>/dev/null | \\
  sed \'s#^.*//[^/]*/#^\\\\./#g\' | \\
  sed \'s#[.][^.]*$##\' | \\
  tee /tmp/files.txt | \\
  less

# Find all files (not directories) that correspond to media uploads
#   ... NOT matching the ones we found in the database
#   ... and see them in the less pager in case there\'s a lot of output
find ./wp-content/uploads/20* -type f | \\
  grep -E -f /tmp/files.txt -v | \\
  less
(奇怪的sed 命令可能会被一种幻想所取代wp db query 相反)

您可以修改grep 通过添加命令-c (统计匹配/不匹配的文件)或删除-v (查看数据库中存在匹配项的文件)。