使用Django Rest API创建POST接口时遭遇get_extra_actions属性错误
问题:POST请求添加数据库记录时触发AttributeError错误
错误信息
AttributeError: 'function' object has no attribute 'get_extra_actions'
开发环境
使用VS Code开发
相关代码
views.py
class newUser(generics.ListCreateAPIView): def createUser(self, request): name: request.POST['name'] phone: request.POST['phone'] email: request.POST['email'] newUser = User(name=name, phone=phone, email=email) User.save() return newUser
路由代码
router = routers.DefaultRouter() router.register(r'user',UserViewSet, basename='user') router.register(r'createuser',newUser, basename='createuser') urlpatterns = [ path('admin/', admin.site.urls), # path('api/users/', UserViewSet.as_view({'get': 'list'})), ] urlpatterns += router.urls
堆栈跟踪
"C:\Users\Christian\AppData\Local\Programs\Python\Python38\lib\site-packages\django\urls\resolvers.py", line 494, in check for pattern in self.url_patterns: File "C:\Users\Christian\AppData\Local\Programs\Python\Python38\lib\site-packages\django\utils\functional.py", line 57, in __get__ res = instance.__dict__[self.name] = self.func(instance) File "C:\Users\Christian\AppData\Local\Programs\Python\Python38\lib\site-packages\django\urls\resolvers.py", line 715, in url_patterns patterns = getattr(self.urlconf_module, "urlpatterns", self.urlconf_module) File "C:\Users\Christian\AppData\Local\Programs\Python\Python38\lib\site-packages\django\utils\functional.py", line 57, in __get__ res = instance.__dict__[self.name] = self.func(instance) File "C:\Users\Christian\AppData\Local\Programs\Python\Python38\lib\site-packages\django\urls\resolvers.py", line 708, in urlconf_module return import_module(self.urlconf_name) File "C:\Users\Christian\Documents\VS_projects\python\gestionale\gestionale\urls.py", line 30, in <module> urlpatterns += router.urls File "C:\Users\Christian\AppData\Local\Programs\Python\Python38\lib\site-packages\rest_framework\routers.py", line 77, in urls self._urls = self.get_urls() File "C:\Users\Christian\AppData\Local\Programs\Python\Python38\lib\site-packages\rest_framework\routers.py", line 338, in get_urls urls = super().get_urls() File "C:\Users\Christian\AppData\Local\Programs\Python\Python38\lib\site-packages\rest_framework\routers.py", line 236, in get_urls routes = self.get_routes(viewset) File "C:\Users\Christian\AppData\Local\Programs\Python\Python38\lib\site-packages\rest_framework\routers.py", line 152, in get_routes extra_actions = viewset.get_extra_actions() AttributeError: type object 'newUser' has no attribute 'get_extra_actions'
解决方案
1. 核心错误原因
DefaultRouter.register()仅支持注册ViewSet类,但你传入的newUser是继承自generics.ListCreateAPIView的普通APIView类,只有ViewSet才包含get_extra_actions()方法,因此路由器调用该方法时触发错误。
2. 两种修复方案
方案一:直接用path()注册APIView
修改路由代码,不再通过路由器注册newUser:
router = routers.DefaultRouter() router.register(r'user', UserViewSet, basename='user') urlpatterns = [ path('admin/', admin.site.urls), path('api/createuser/', newUser.as_view(), name='createuser') # 直接绑定视图 ] urlpatterns += router.urls
方案二:将newUser改为ViewSet(推荐)
调整views.py,让视图继承viewsets.ViewSet,符合REST框架的路由器规范:
from rest_framework import viewsets from rest_framework.response import Response class newUser(viewsets.ViewSet): def create(self, request): # 修复赋值语法,用=代替: name = request.data.get('name') phone = request.data.get('phone') email = request.data.get('email') # 修复save()调用方式:实例调用而非类调用 new_user = User(name=name, phone=phone, email=email) new_user.save() # 返回标准DRF响应,而非直接返回模型实例 return Response({ "id": new_user.id, "name": new_user.name, "phone": new_user.phone, "email": new_user.email })
修改后可继续使用router.register(r'createuser', newUser, basename='createuser')注册。
3. 额外注意事项
- 变量赋值必须用等号
=,原代码中的冒号:是语法错误 - 保存模型数据时,需调用实例对象的
save()方法,不能直接调用类的save() - DRF中优先使用
request.data替代request.POST,支持JSON、表单等多种请求格式
内容的提问来源于stack exchange,提问作者Christian Termo
相关产品推荐
相关产品推荐

