مدیریت خطاها و پیامهای خطا در GraphQL با FastAPI و Strawberry
در GraphQL، خطاها معمولاً به صورت ساختاریافته در پاسخها بازگردانده میشوند و به کلاینت اجازه میدهند تا تشخیص دهد چه چیزی اشتباه بوده است. در Strawberry میتوان مدیریت خطاها را هم در سطح Resolver و هم در سطح Middleware انجام داد.
۱. مدیریت خطا در Resolver
سادهترین روش مدیریت خطا، استفاده از try/except
در Resolverها است. این روش امکان میدهد پیامهای خطای سفارشی به کاربر بازگردانده شود:
@strawberry.type
class UserMutation:
@strawberry.mutation
def create_user(self, info, email: str, password: str) -> UserType:
db: Session = info.context["db"]
try:
if len(password) < 6:
raise ValueError("Password must be at least 6 characters long")
if "@" not in email:
raise ValueError("Invalid email address")
new_user = UserModel(email=email, password=password)
db.add(new_user)
db.commit()
db.refresh(new_user)
return UserType(
id=new_user.id,
email=new_user.email,
created_at=str(new_user.created_at),
updated_at=str(new_user.updated_at),
tasks=[]
)
except Exception as e:
raise ValueError(f"Error creating user: {str(e)}")
۲. استفاده از استثناهای سفارشی
میتوان کلاسهای Exception مخصوص به پروژه تعریف کرد و آنها را در Resolverها استفاده نمود:
class UserAlreadyExistsError(Exception):
pass
@strawberry.type
class UserMutation:
@strawberry.mutation
def create_user(self, info, email: str, password: str) -> UserType:
db: Session = info.context["db"]
existing_user = db.query(UserModel).filter(UserModel.email == email).first()
if existing_user:
raise UserAlreadyExistsError(f"User with email {email} already exists")
new_user = UserModel(email=email, password=password)
db.add(new_user)
db.commit()
db.refresh(new_user)
return UserType(
id=new_user.id,
email=new_user.email,
created_at=str(new_user.created_at),
updated_at=str(new_user.updated_at),
tasks=[]
)
۳. پیامهای خطا در پاسخ GraphQL
زمانی که یک Exception در Resolver ایجاد شود، Strawberry آن را به بخش errors
پاسخ GraphQL اضافه میکند:
{
"data": null,
"errors": [
{
"message": "User with email user@example.com already exists",
"locations": [{"line": 2, "column": 3}],
"path": ["createUser"]
}
]
}
۴. نکات مهم
- خطاهای ولیدیشن و منطقی را داخل Resolver مدیریت کنید.
- برای خطاهای پیشرفته میتوان Middleware سفارشی ایجاد کرد تا همه خطاها یکدست شوند.
- اطمینان حاصل کنید که پیامهای خطا اطلاعات حساس مثل رمز عبور را افشا نمیکنند.
با این روشها، کاربران GraphQL میتوانند بفهمند چه چیزی اشتباه شده و توسعهدهندگان نیز به راحتی میتوانند خطاها را ردیابی و مدیریت کنند.