使用FastAPI从MongoDB获取数据时遭遇500内部服务器错误求助
问题描述
我编写了一个用于从MongoDB获取数据的FastAPI接口,当尝试查询集合中的所有交易数据时,遇到了500内部服务器错误。已确认MongoDB连接正常、集合存有数据,FastAPI单独运行无异常,仅查询集合时出错。
代码示例
from fastapi import FastAPI, HTTPException from pymongo import MongoClient from bson import json_util import json app = FastAPI() # MongoDB connection details mongo_url = "mongodb://localhost:27017/" client = MongoClient(mongo_url) db = client.banking collection = db.transaction_data @app.get("/") async def root(): return {"message": "Hello World"} # all transactions @app.get("/transactions") async def get_transactions(): try: transactions = collection.find() # Transform the cursor to a list of dictionaries transaction_list = [transaction for transaction in transactions] # Return the list of dictionaries return transaction_list except: raise HTTPException(status_code=404, detail="Transactions not found")
错误现象
Swagger文档返回500内部服务器错误,提示"Internal Server Error"
解决方法
1. 问题根源
MongoDB查询返回的文档包含ObjectId这类BSON专属类型,FastAPI默认的JSON序列化器无法处理该类型,导致返回响应时触发序列化失败,抛出500错误。另外你的空except:语句没有捕获到这个返回阶段的异常(异常发生在return序列化时,而非查询循环过程中),还错误地返回了404状态码(这是资源不存在的状态,不符合当前服务器内部错误的场景)。
2. 具体修复方案
方案一:利用json_util处理BSON序列化
使用bson.json_util工具完成BSON到JSON的转换,再转为Python字典返回:
@app.get("/transactions") async def get_transactions(): try: transactions = collection.find() # 用json_util处理BSON类型,再解析为Python字典列表 transaction_list = json.loads(json_util.dumps(transactions)) return transaction_list except Exception as e: # 打印错误信息便于调试 print(f"Debug Error: {str(e)}") raise HTTPException(status_code=500, detail=f"Server error: {str(e)}")
方案二:手动转换ObjectId为字符串
遍历查询结果时,手动将_id字段转换为字符串类型:
@app.get("/transactions") async def get_transactions(): try: transactions = collection.find() transaction_list = [] for transaction in transactions: # 将MongoDB的ObjectId转为普通字符串 transaction["_id"] = str(transaction["_id"]) transaction_list.append(transaction) return transaction_list except Exception as e: print(f"Debug Error: {str(e)}") raise HTTPException(status_code=500, detail=f"Server error: {str(e)}")
3. 额外优化建议
- 避免使用空的
except:,明确捕获Exception并打印错误信息,方便快速定位问题 - 状态码要匹配场景:服务器内部错误返回500,404仅用于确实找不到资源的情况
内容的提问来源于stack exchange,提问作者Russel Osiemo
相关产品推荐
相关产品推荐

