Google Storage Transfer事件驱动模式NOT_FOUND错误排查与解决求助
问题描述
已配置Google Storage Transfer Service将对象从一个GCS桶复制至另一个GCS桶,目前98%的对象复制成功,但有2%的对象复制失败,错误详情为NOT_FOUND,错误信息:
No such object: source-bucket-name/path/to/object/ObjectName.json
核查后确认该对象实际存在。由于GCS会在对象创建完成时(OBJECT_FINALIZE事件)向Pub/Sub发送通知,无法理解该错误产生的原因。
配置信息
Config Connector配置
--- apiVersion: storage.cnrm.cloud.google.com/v1beta1 kind: StorageNotification metadata: name: source-notification spec: bucketRef: name: source-bucket-name payloadFormat: JSON_API_V1 topicRef: name: my-notification-topic eventTypes: - "OBJECT_FINALIZE" - "OBJECT_METADATA_UPDATE" - "OBJECT_DELETE" - "OBJECT_ARCHIVE" --- apiVersion: pubsub.cnrm.cloud.google.com/v1beta1 kind: PubSubTopic metadata: name: my-notification-topic spec: messageRetentionDuration: 2678400s # 31 days --- apiVersion: pubsub.cnrm.cloud.google.com/v1beta1 kind: PubSubSubscription metadata: name: my-notification-subscription spec: ackDeadlineSeconds: 300 enableExactlyOnceDelivery: false retainAckedMessages: false topicRef: name: my-notification-topic expirationPolicy: ttl: ""
手动配置的Storage Transfer服务
Scheduling mode: Event driven Source Type: Google Cloud Storage Name: source-bucket-name Folder path: path/to/source Event stream: Pub/sub subscription name: projects/my-projects/subscriptions/my-notification-subscription Filters: None Destination Type: Google Cloud Storage Name: destination-bucket-name Folder path: path/to/destination Data handling options: Metadata options: ACL: Use destination bucket's object ACLs KMS key: Use destination bucket's encryption settings Storage class: Use destination bucket's storage class Temporary hold: Preserve object's original temporary hold status Time created: Do not preserve source object's time created When to overwrite: Always When to delete: Never
需求:彻底解决该NOT_FOUND错误,或找到复制失败对象的可行方案。
可能的原因与解决办法
1. 事件触发与对象状态的时间差
OBJECT_FINALIZE事件触发时,对象虽已完成写入,但GCS跨区域存储的一致性模型可能存在短暂读取延迟。Storage Transfer Service收到事件立即复制时,对象可能未在所有副本节点同步完成,导致读取失败。
解决办法:
- 若使用自定义订阅处理逻辑,在触发复制前添加10-30秒延迟;若依赖Transfer原生事件驱动,调整重试策略增加重试间隔。
2. 对象路径编码问题
失败对象的文件名若包含特殊字符(空格、Unicode字符),Pub/Sub事件中的路径编码可能与实际对象路径不匹配,导致Transfer无法定位对象。
解决办法:
- 用
gsutil ls命令精确匹配对象路径,对比事件消息中的路径是否一致;检查Transfer源文件夹路径是否存在多余斜杠或编码错误。
3. 权限与访问范围问题
Transfer服务账号可能缺少源桶的storage.objects.get权限,或源桶受VPC Service Controls限制,导致权限不足被伪装成NOT_FOUND错误。
解决办法:
- 确认Transfer使用的服务账号(默认
transfer-service@system.gserviceaccount.com)拥有源桶的读取权限;检查VPC Service Controls是否允许Transfer服务访问源桶。
4. 对象生命周期或版本冲突
源桶若启用版本控制,或对象在事件触发后被修改/归档,Transfer可能尝试读取已失效的版本,导致错误。
解决办法:
- 检查源桶版本控制设置,确认Transfer读取的是对象当前有效版本;调整生命周期规则的时间窗口,确保Transfer有足够时间完成复制。
5. 失败对象的补救方案
若无法彻底避免错误,可采用以下措施:
- 定期运行一次性Transfer任务,扫描源桶未复制成功的对象进行补充复制;
- 导出Transfer失败日志,用脚本通过
gsutil cp或GCS API批量重新触发复制。
内容的提问来源于stack exchange,提问作者Darkttd
相关产品推荐
相关产品推荐

