使用Python上传PDF到S3存储桶时出现[Errno 13] Permission denied报错
S3批量上传PDF触发[Errno 13]权限拒绝问题
复现场景
编写Python脚本批量扫描本地指定目录下的PDF,上传到AWS S3存储桶,运行时直接抛出权限类报错,对应代码如下:
import pathlib all_pdfs=pathlib.Path(base_folder+'\\selenium_controller\\psdf\\') file_path=all_pdfs print(file_path) for file in all_pdfs.glob('*.pdf'): print(file) file_main=str(str(file).split("\\")[-1]) aws_textract = AWSTextract() s3_client = aws_textract.connect_S3() aws_textract.upload_to_s3(s3_client, str(file_path),str(file_main) )
运行后抛出的报错内容为:
[Errno 13] Permission denied: 'E:\\all_projects\\v1.0.0\\static\\selenium_controller\\psdf'
根因定位
该报错并非系统层面的文件夹权限配置异常,本质是代码传参逻辑错误:
- 核心错误:调用
upload_to_s3方法时传入的是目录路径,不是具体文件路径 - 代码中定义的
file_path指向psdf文件夹的目录路径,并非某一个PDF文件的完整路径 - 上传方法内部需要打开本地文件读取字节流,Windows系统下尝试以文件读取模式打开文件夹时,会直接抛出[Errno 13]权限拒绝。报错信息里的路径也能对应这个逻辑——抛错的路径刚好是psdf目录本身,不是某一个PDF文件。
代码修正方案
- 替换错误的传参:循环内遍历得到的
file对象就是当前PDF的完整路径,调用上传方法时把原来传的str(file_path)换成str(file) - 优化初始化逻辑:将AWS Textract实例、S3客户端的初始化操作挪到循环外部,原代码每遍历一个PDF就新建一次连接,既浪费资源,还容易触发AWS接口的访问频率限制,仅在循环外初始化一次即可
- 优化路径拼接写法:使用pathlib原生的路径拼接逻辑代替手动拼接反斜杠的字符串写法,避免路径分隔符写死带来的跨平台兼容问题
- 简化文件名提取逻辑:pathlib路径对象自带
name属性可以直接拿到文件名,不需要手动用split切字符串,避免特殊文件名导致的切分错误
修正后的参考代码
from pathlib import Path # 循环外仅初始化一次客户端 aws_textract = AWSTextract() s3_client = aws_textract.connect_S3() # 原生路径拼接,替代手动拼接反斜杠 target_dir = Path(base_folder) / "selenium_controller" / "psdf" print(target_dir) for file in target_dir.glob("*.pdf"): print(file) # 传入当前文件的完整路径,直接获取文件本名 aws_textract.upload_to_s3(s3_client, str(file), file.name)
排查提示:如果修正传参后仍出现同类权限报错,需要检查当前运行脚本的系统账号是否对该目录有读取权限,同时确认目标PDF没有被其他进程(如PDF阅读器、云同步软件)锁定占用。
内容的提问来源于stack exchange,提问作者King
相关产品推荐
相关产品推荐

