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

使用Spark读取MongoDB时分区失败的授权问题排查

问题描述

尝试使用MongoDB Spark Connector读取MongoDB数据时,能够通过Spark打印数据Schema,但执行show()展示数据时出现分区失败错误,已尝试多种分区器选项仍未解决。

环境信息

  • Spark版本:3.3.0
  • MongoDB版本:5.5.0
  • Connector版本:10.2.0

报错的Spark代码

from pyspark.sql import SparkSession
from pyspark import SparkContext
spark = SparkSession.builder.appName(job_name).getOrCreate()
url = "mongodb://ReadUser:Password123@mongo-db.test.app:27017/db_name"
df = (
    spark
    .read
    .format("mongodb")
    .option('connection.uri',url)
    .option("database", "db_name")
    .option("collection","collection1")
    .option('partitioner','com.mongodb.spark.sql.connector.read.partitioner.ShardedPartitioner')
    .load()
)
df.printSchema()
df.show()

可正常运行的Python代码(pymongo)

from pymongo import MongoClient
url = "mongodb://ReadUser:Password123@mongo-db.test.app:27017/db_name"
client=MongoClient(url)
db=client["db_name"]
table = db["collection1"]
x = table.find()
for data in x:
    print(data)

Spark错误日志

com.mongodb.spark.sql.connector.exceptions.MongoSparkException: Partitioning failed.

root
 |-- _id: string (nullable = true)
 |-- created_date: double (nullable = true)
 |-- code: integer (nullable = true)
 |-- expiry_time: double (nullable = true)
 |-- mail_res: void (nullable = true)
 |-- noOf_code: integer (nullable = true)
 |-- type: string (nullable = true)
 |-- proposalId: void (nullable = true)
 |-- code_s: void (nullable = true)
 |-- twillow_res: void (nullable = true)
 |-- user_id: string (nullable = true)

An error occurred while calling o118.showString.
: com.mongodb.spark.sql.connector.exceptions.MongoSparkException: Partitioning failed.
    at com.mongodb.spark.sql.connector.read.partitioner.PartitionerHelper.generatePartitions(PartitionerHelper.java:69)
    ...
Caused by: com.mongodb.MongoQueryException: Query failed with error code 13 with name 'Unauthorized' and error message 'not authorized on config to execute command { find: "collections", filter: { _id: "db_name.collection1" }, projection: { _id: 1, timestamp: 1, uuid: 1, dropped: 1, key: 1 }, limit: 1, singleBatch: true, $db: "config", lsid: { id: UUID("a835c704-429c-4b0e-99f7-739d28105be3") } }' on server mongo-db.test.app:27017
    ...

问题原因分析

从错误日志的Unauthorized报错可明确:

  1. 当前使用的ShardedPartitioner分区器需要访问MongoDB的config数据库中的collections集合,以获取分片集合元数据来生成分区。
  2. 你的ReadUser账号仅拥有目标数据库db_name的读取权限,无访问config数据库的权限,因此触发授权失败。
  3. pymongo代码能正常运行是因为它直接读取目标集合,不需要访问config库获取分片元数据。

解决方案

  1. 更换分区器:若MongoDB集群不是分片集群,或不需要基于分片键分区,改用无需访问config库的分区器,比如MongoSinglePartitioner(单分区读取):
    .option('partitioner','com.mongodb.spark.sql.connector.read.partitioner.MongoSinglePartitioner')
    
  2. 添加权限:若必须使用ShardedPartitioner,给ReadUser账号添加config数据库的只读权限,执行MongoDB命令:
    use admin
    db.grantRolesToUser("ReadUser", [{ role: "read", db: "config" }])
    
  3. 确认集群类型:检查MongoDB是否为分片集群,若为单节点或副本集,使用ShardedPartitioner本身不合理,会触发不必要的config库访问。

内容的提问来源于stack exchange,提问作者NIKHIL SUTHAR

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.04 11:07:39