Firestore Ruby如何认证?(权限拒绝问题)
Firestore Ruby客户端权限拒绝问题与用户认证方案
问题背景
使用Ruby的firestore gem访问Firestore,所有配置均正常,但启用文档读写规则时触发**权限拒绝(Permission denied)**错误。开放全文档读写权限(如规则设为allow read, write: if true;)时可正常返回数据,确认问题由Firestore安全规则导致。
客户端认证代码:
creds = Rails.application.credentials.firestore Google::Cloud::Firestore.configure do |config| config.project_id = creds[:config][:projectId] config.credentials = creds[:service_account].to_h config.emulator_host = "localhost:8888" if Rails.env.development? end @client = Google::Cloud::Firestore.new @client.col(collection_name).get
错误信息:
GRPC::PermissionDenied: 7: false for 'list' @ L83. debug_error_string:{UNKNOWN:Error received from peer ipv4:127.0.0.1:8888 {created_time:"2022-11-18T17:44:53.265761-08:00", grpc_status:7, grpc_message:"\nfalse for \'list\' @ L83"}}
核心疑问
- Firestore Ruby是否支持用户认证?
- 若支持,具体如何实现?(目前仅知道可通过Admin创建令牌,但未找到用户登录API)
解决方案
Firestore Ruby客户端本身不提供用户登录流程的API,用户认证属于Firebase Auth的范畴,需结合前端登录+服务端验证/令牌传递的方式实现,以下是两种可行方案:
方案1:使用Firebase Admin SDK绕过规则(服务端权限控制)
如果服务端需要不受Firestore安全规则限制访问数据,可改用Firebase Admin SDK for Ruby:
- 确保服务账号拥有
Cloud Datastore User或更高权限(通过Google Cloud IAM配置)。 - 用Admin SDK初始化客户端,它会自动绕过Firestore安全规则:
require "firebase_admin" # 初始化Admin SDK FirebaseAdmin::App.initialize_app( credential: FirebaseAdmin::Credentials.from_service_account(creds[:service_account].to_h), project_id: creds[:config][:projectId] ) # 获取Firestore实例 firestore = FirebaseAdmin::Firestore.client firestore.col(collection_name).get
注:此方案需在服务端自行实现权限逻辑,根据用户身份过滤数据。
方案2:传递用户ID令牌,模拟客户端身份受规则约束
若需让请求受Firestore安全规则判断,可在初始化Firestore客户端时传入用户的ID令牌:
- 前端通过Firebase Auth完成登录,获取ID令牌并传给服务端。
- 服务端用该令牌初始化Firestore客户端:
# 从前端获取的用户ID令牌 user_id_token = "前端传来的ID令牌字符串" @client = Google::Cloud::Firestore.new( project_id: creds[:config][:projectId], credentials: creds[:service_account].to_h, auth: user_id_token ) # 此时请求会带上用户身份,Firestore将按安全规则校验权限 @client.col(collection_name).get
注:ID令牌需在前端通过Firebase Auth的登录接口获取,服务端可通过Firebase Admin SDK验证令牌合法性,避免伪造。
关于“创建令牌”的说明
你提到的通过Ruby Admin创建令牌,指的是自定义令牌,用于让客户端(如移动端/前端)进行登录,而非服务端自身使用。创建示例:
auth = FirebaseAdmin::Auth.auth custom_token = auth.create_custom_token("用户UID") # 将custom_token返回给前端,前端用它完成Firebase Auth登录
内容的提问来源于stack exchange,提问作者orangesoda
相关产品推荐
相关产品推荐

