FastAPI+Strawberry构建GraphQL API时类型循环导入问题解决
Strawberry 跨文件双向关联类型循环导入修复
你当前代码的报错来自三个编写疏漏,按如下方式修改即可解决:
- 双向关联的类型禁止在文件顶层互相导入,否则会形成循环导入链
- 关联字段的返回类型需要用字符串前向引用,配合函数内延迟导入加载依赖
- 现有Department类漏写了私有instance字段、from_instance漏传instance参数、employees返回类型注解错误,会导致运行时报错
修改后 Employee 定义
import strawberry from app.models.employee import Employee as EmployeeModel from app.api.v1.definitions.profile import Profile # 移除顶层导入Department的代码 @strawberry.type class Employee: id: str email: str instance: strawberry.Private[EmployeeModel] @strawberry.field def department(self) -> "Department": # 函数内部延迟导入,仅在字段被解析时加载依赖,不会触发顶层循环 from app.api.v1.definitions.department import Department return Department.from_instance(self.instance.department) @strawberry.field def profile(self) -> Profile: return Profile.from_instance(self.instance.profile) @classmethod def from_instance(cls, instance: EmployeeModel): return cls( instance=instance, id=instance.id, email=instance.email, )
修改后 Department 定义
import strawberry from typing import List from app.models.department import Department as DepartmentModel @strawberry.type class Department: id: int name: str # 补全私有instance字段 instance: strawberry.Private[DepartmentModel] @strawberry.field def employees(self) -> List["Employee"]: # 修正返回类型为Employee列表,用字符串做前向引用 from app.api.v1.definitions.employee import Employee return [Employee.from_instance(employee) for employee in self.instance.employees] @classmethod def from_instance(cls, instance: DepartmentModel): return cls( # 补全instance参数传递 instance=instance, id=instance.id, name=instance.name, )
注意事项
- 所有跨文件的双向关联类型,都遵循「字符串前向引用+字段方法内延迟导入」的模式即可彻底避免循环导入,Strawberry启动时会自动完成类型解析,不需要提前导入依赖
strawberry.Private标记的字段仅内部使用,不会出现在GraphQL对外的Schema中,关联ORM实例的字段必须加该标记,否则会被当做普通字段暴露或触发类型解析错误
内容的提问来源于stack exchange,提问作者user1314147
相关产品推荐
相关产品推荐

