NilCoalescing / djangochannelsrestframework

A Rest-framework for websockets using Django channels-v4
https://djangochannelsrestframework.readthedocs.io/en/latest/
MIT License
603 stars 84 forks source link

[BUG] It's impossible to fully use a REAL WORLD viewset via view_as_consumer #163

Closed shadow3312 closed 11 months ago

shadow3312 commented 1 year ago

Describe the bug It seems like the view_as_consumer is a kind of kiddie stuff that works well only for "tuto views" (Generic ones with those 4 basic actions) when there is a new action in the viewset, method not allowed is thrown.

I have a custom viewset that don't inherit from GenericAPIView but from this one I made https://github.com/shadow3312/drf-scrud/blob/main/django-crud/scrud/views.py

Like you can see, there are some custom actions that work well in my REST API and I don't want to rewrite them in a consumer. My viewset is set, I just want all my actions to be mapped when I call view_as_consumer. Is there a workaround for this ?

To Reproduce Steps to reproduce the behavior:

  1. .. Install the package
  2. .. View definition above
  3. .. In routing.py: python websocket_urlpatterns = [ re_path(r"^ws/message/", view_as_consumer (views.MessageViewset.as_view({'get': 'search', 'post': 'create'}))), ]
  4. ... {"action": "search"} in frontend

Note: MessageViewset subclasses The ScrudViewset linked above

I get 405 Method "search" not allowed.

Expected behavior Map all the actions available in the viewset. Including search.

hishnash commented 11 months ago

Soory for the slow response here>

view_as_consumer maps Restful actions to HTTP methods.

https://djangochannelsrestframework.readthedocs.io/en/latest/consumers.html#djangochannelsrestframework.consumers.view_as_consumer

So if you want to call the search function here you need to send the action retrieve over the WebSocket message.

You can change this by using mapped_actions options


python websocket_urlpatterns = [
     re_path(
        r"^ws/message/",
        view_as_consumer(
            views.MessageViewset.as_view({'get': 'search', 'post': 'create'}),
           mapped_actions = {"search": "get"}
        )
    ), 
]