如果文件不存在,则毫无例外地从 GCS 中删除

Posted

技术标签:

【中文标题】如果文件不存在,则毫无例外地从 GCS 中删除【英文标题】:Delete from GCS without exception if file is not present 【发布时间】:2020-01-14 16:19:25 【问题描述】:

我正在通过 python 调用一个 shell 脚本。

在脚本中我使用gsutil rmgsutil cp 命令。

但是每当这两个命令中的任何一个在不存在的 gcp 路径上运行时,都会出错。

例如:当我尝试时:

gsutil rm -r gs://some-bucket/somepath-not-present/

我收到一个错误:

CommandException: 1 files/objects could not be removed.

最后脚本的返回码是 1。即使我的代码执行得很好。我希望脚本在找不到路径时不会出错。

有没有办法绕过这个。我已经尝试了来自 linux 的 ||,但它似乎不起作用。

【问题讨论】:

您能否详细说明“没有任何异常”是什么意思?您的意思是尽管出现错误,但仍继续使用 shell 脚本?或者只是不打印错误消息?还是别的什么? 我正在运行一系列的 shell 命令,这些命令写在一个脚本中,通过 python 调用。它有'gsutil rm''cp' 命令。但是我不希望脚本返回 1,如果路径不存在的话。我是否必须处理脚本中的错误,使其返回 0 ?? 【参考方案1】:

如果您在可能受gsutil 打印的异常影响的另一个脚本中使用gsutil,您可以简单地尝试将stderr 重定向到/dev/null,如下所示:

gsutil rm -r gs://some-bucket/somepath-not-present/ 2> /dev/null

但是,请注意,此时您将开始忽略该命令生成的任何错误。如果你echo $?,你仍然会得到1的错误代码,它可以告诉你文件不存在或发生了其他异常。

编辑:

如果你想以退出代码 0 退出脚本,你可以这样做

gsutil rm -r gs://some-bucket/somepath-not-present/ || exit 0

或者如果你只是想让命令返回 0,你可以使用

gsutil rm -r gs://some-bucket/somepath-not-present/ || true

【讨论】:

这听起来很傻。但是,如果路径不存在,是否有返回码为 0。实际上,我正在运行一系列用脚本编写的 shell 命令,该脚本通过 python 调用。如果路径不存在,我不希望脚本返回 1。 @ezvine 您可以随时将|| exit 0 添加到此行的末尾以0(成功)退出,以防gsutil rm 以1 失败 这会导致从整个脚本中退出。或者仅适用于脚本中的特定命令。即,脚本的其余部分会正常执行吗? 哦,是的 - 如果这不是您正在运行的唯一命令,您需要附加 || true 而不是退出命令。那应该继续脚本 非常感谢。这件事有效..请将他添加到您的答案中..【参考方案2】:

令我惊讶的是,Google 尚未解决此问题。我遇到了同样的问题,我依赖构建脚本来继续运行,即使存储桶已经是空的。

我想出了以下解决方法:

if [[ $(gsutil du gs://my-bucket | wc -l) -gt 0 ]]; then gsutil -m rm -rf gs://my-bucket/*; fi

它基本上计算存储桶中的对象数量,如果计数大于零,则仅运行gsutil rm

【讨论】:

如果文件夹中的文件数量很大,我认为做一个完整的 du 不是一个好主意。这将是一个耗时的命令。 || true 是上面答案中建议的一个不错的选择。或者也许尝试gsutil ls gs://my-bucket | head -1 | wc -l,并且只有当这个命令成功并且>1,然后删除文件。 是的,这很好。在我们的例子中,源文件夹的文件数量很少会很大,所以老实说我并没有真正考虑性能。我尝试了|| true 解决方案,但我在构建管道中使用它,它仍然导致构建脚本失败。我需要一个允许脚本继续运行的解决方案。

以上是关于如果文件不存在,则毫无例外地从 GCS 中删除的主要内容,如果未能解决你的问题,请参考以下文章

文件操作

Python知识点梳理:文件处理

shell脚本之对不存的文件进行记录

检查列表中的对象是不是存在,如果在 R 中不存在则将其删除

Ant:如果不存在,则创建目录

python集合以及数据类型的总结