You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

前端React+Supabase Auth,后端Flask对接Supabase RLS存储权限问题

解决方案:Supabase Storage 上传时传递用户认证信息

你的核心问题是错误地将认证头放在了file_options参数中——这个参数是用来设置文件的元数据(比如MIME类型、自定义文件属性),而非HTTP请求头,所以Supabase无法识别该用户的认证状态。

下面提供两种可行的修正方案:

方案一:基于用户Token创建临时Supabase客户端

直接用前端传递的用户access token初始化一个临时Supabase客户端,该客户端发起的所有请求都会自动携带用户认证信息,完美适配RLS策略。

修改后的upload_file函数:

from supabase import create_client, Client

# 全局变量:替换成你的Supabase项目URL和Anon密钥
SUPABASE_URL = "你的Supabase URL"
SUPABASE_ANON_KEY = "你的Supabase Anon密钥"

def upload_file(file_name, bucket, token):
    # 创建临时Supabase客户端
    supabase: Client = create_client(SUPABASE_URL, SUPABASE_ANON_KEY)
    # 给客户端设置用户的认证Token
    supabase.postgrest.auth(token)
    # 同步给Storage模块设置认证头
    supabase.storage._request.headers["Authorization"] = f"Bearer {token}"
    
    with open(file_name, "rb") as f:
        supabase.storage.from_(bucket).upload(
            file=f,
            path=file_name,
            file_options={
                "content-type": "image/jpeg"
            },
        )

方案二:手动调用底层API,自定义请求头

如果你不想创建新的客户端实例,可以直接调用Storage客户端的底层_request方法,手动构造上传请求并添加认证头:

def upload_file(file_name, bucket, token):
    storage_client = supabase.storage.from_(bucket)
    with open(file_name, "rb") as f:
        # 构造上传接口的路径
        request_path = f"/object/{bucket}/{file_name}"
        # 发起PUT请求,携带认证头和文件数据
        response = storage_client._request(
            method="PUT",
            path=request_path,
            headers={
                "Authorization": f"Bearer {token}",
                "Content-Type": "image/jpeg"
            },
            data=f
        )
        # 检查响应状态,处理错误
        if response.status_code not in (200, 201):
            raise Exception(f"上传失败:{response.text}")

额外注意事项

  1. RLS策略配置:确保你已经为Supabase Storage的produtos桶配置了正确的RLS策略,比如允许认证用户上传/访问指定路径,示例策略:
    CREATE POLICY "认证用户可上传产品图片" ON storage.objects
    FOR INSERT WITH CHECK (
      auth.role() = 'authenticated' 
      AND bucket_id = 'produtos'
      AND owner = auth.uid()
    );
    
  2. Token验证:你的verify_token函数必须使用Supabase项目的JWT秘钥(在项目设置→API→JWT Secret)来验证token的有效性,避免无效/过期token被使用。
  3. 文件路径优化:当前代码用原始文件名作为存储路径,建议结合user_id或cdProduto构建更安全的路径(比如produtos/{user_id}/{cdProduto}/{nrImagem}.jpg),配合RLS策略进一步限制访问范围。

内容的提问来源于stack exchange,提问作者Augusto Peres

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.19 20:03:21