FastAPI PostgreSQL删除操作触发500内部服务器错误排查
问题原因分析:PostgreSQL + FastAPI删除操作中
cursor.fetchone()报错psycopg2.ProgrammingError: no results to fetch 核心原因
PostgreSQL的常规DELETE语句执行完成后,不会返回被删除的行数据。你的代码里执行完DELETE后直接调用cursor.fetchone(),但此时游标根本没有可获取的结果集——不管目标ID存在与否,只要是普通DELETE,都不会产生返回结果,所以必然触发no results to fetch的编程错误。
哪怕ID存在、记录确实被删除了,普通DELETE也不会返回任何数据,这就是为什么你看到记录被删但仍报500的原因。
解决方案
有两种靠谱的修正方式,根据你的需求选择:
方式1:获取被删除的行数据(用RETURNING子句)
如果需要拿到被删除的post内容,修改DELETE语句,加上RETURNING *让PostgreSQL返回被删除的行:
@app.delete("/posts/{id}", status_code=status.HTTP_204_NO_CONTENT) def delete_post(id: int): print("ID IS ",id) # 加上RETURNING *,让DELETE返回被删除的行 cursor.execute("""DELETE FROM public."Posts" WHERE id = %s RETURNING *""", (id,)) deleted_post = cursor.fetchone() conn.commit() if deleted_post is None: raise HTTPException(status_code=status.HTTP_404_NOT_FOUND, detail=f"Post with {id} not found") return Response(status_code=status.HTTP_204_NO_CONTENT)
另外注意:id本身是int类型,不需要转成str(id),直接传(id,)更合理。
方式2:仅判断是否有行被删除(用cursor.rowcount)
如果不需要被删除的数据,只需要确认是否存在对应记录,直接用游标rowcount属性获取受影响的行数即可:
@app.delete("/posts/{id}", status_code=status.HTTP_204_NO_CONTENT) def delete_post(id: int): print("ID IS ",id) cursor.execute("""DELETE FROM public."Posts" WHERE id = %s""", (id,)) conn.commit() # 受影响行数为0,说明没有找到对应ID的记录 if cursor.rowcount == 0: raise HTTPException(status_code=status.HTTP_404_NOT_FOUND, detail=f"Post with {id} not found") return Response(status_code=status.HTTP_204_NO_CONTENT)
这种方式不需要修改DELETE语句,更轻量。
内容的提问来源于stack exchange,提问作者Devang Sanghani
相关产品推荐
相关产品推荐

