Understanding django channels - QueryAuthMiddleware











up vote
0
down vote

favorite












How to write custom authentication of user, that connects to chat over ws:// protocol? This user is on the other side of Django app, he is the mobile user, connecting websocket via ws:// from mobile app. I tried to test websocket with chrome extenshion, it couldn't connect to my websocket. I think it was because of authentication.



In Django channels docs it says:




If you have a custom authentication scheme, you can write a custom middleware to parse the details and put a user object (or whatever other object you need) into your scope.Middleware is written as a callable that takes an ASGI application and wraps it to return another ASGI application. Most authentication can just be done on the scope, so all you need to do is override the initial constructor that takes a scope, rather than the event-running coroutine.
Here’s a simple example of a middleware that just takes a user ID out of the query string and uses that:
The same principles can be applied to authenticate over non-HTTP protocols; for example, you might want to use someone’s chat username from a chat protocol to turn it into a user.




from django.db import close_old_connections

class QueryAuthMiddleware:
def __init__(self, inner):
# Store the ASGI application we were passed
self.inner = inner

def __call__(self, scope):
# Look up user from query string (you should also do things like
# check it's a valid user ID, or if scope["user"] is already populated)
user = User.objects.get(id=int(scope["query_string"]))
close_old_connections()
# Return the inner application directly and let it run everything else
return self.inner(dict(scope, user=user))


What query do I need to do? I don't know anything about that user, in fact its anonymous.



Help me, please.










share|improve this question




























    up vote
    0
    down vote

    favorite












    How to write custom authentication of user, that connects to chat over ws:// protocol? This user is on the other side of Django app, he is the mobile user, connecting websocket via ws:// from mobile app. I tried to test websocket with chrome extenshion, it couldn't connect to my websocket. I think it was because of authentication.



    In Django channels docs it says:




    If you have a custom authentication scheme, you can write a custom middleware to parse the details and put a user object (or whatever other object you need) into your scope.Middleware is written as a callable that takes an ASGI application and wraps it to return another ASGI application. Most authentication can just be done on the scope, so all you need to do is override the initial constructor that takes a scope, rather than the event-running coroutine.
    Here’s a simple example of a middleware that just takes a user ID out of the query string and uses that:
    The same principles can be applied to authenticate over non-HTTP protocols; for example, you might want to use someone’s chat username from a chat protocol to turn it into a user.




    from django.db import close_old_connections

    class QueryAuthMiddleware:
    def __init__(self, inner):
    # Store the ASGI application we were passed
    self.inner = inner

    def __call__(self, scope):
    # Look up user from query string (you should also do things like
    # check it's a valid user ID, or if scope["user"] is already populated)
    user = User.objects.get(id=int(scope["query_string"]))
    close_old_connections()
    # Return the inner application directly and let it run everything else
    return self.inner(dict(scope, user=user))


    What query do I need to do? I don't know anything about that user, in fact its anonymous.



    Help me, please.










    share|improve this question


























      up vote
      0
      down vote

      favorite









      up vote
      0
      down vote

      favorite











      How to write custom authentication of user, that connects to chat over ws:// protocol? This user is on the other side of Django app, he is the mobile user, connecting websocket via ws:// from mobile app. I tried to test websocket with chrome extenshion, it couldn't connect to my websocket. I think it was because of authentication.



      In Django channels docs it says:




      If you have a custom authentication scheme, you can write a custom middleware to parse the details and put a user object (or whatever other object you need) into your scope.Middleware is written as a callable that takes an ASGI application and wraps it to return another ASGI application. Most authentication can just be done on the scope, so all you need to do is override the initial constructor that takes a scope, rather than the event-running coroutine.
      Here’s a simple example of a middleware that just takes a user ID out of the query string and uses that:
      The same principles can be applied to authenticate over non-HTTP protocols; for example, you might want to use someone’s chat username from a chat protocol to turn it into a user.




      from django.db import close_old_connections

      class QueryAuthMiddleware:
      def __init__(self, inner):
      # Store the ASGI application we were passed
      self.inner = inner

      def __call__(self, scope):
      # Look up user from query string (you should also do things like
      # check it's a valid user ID, or if scope["user"] is already populated)
      user = User.objects.get(id=int(scope["query_string"]))
      close_old_connections()
      # Return the inner application directly and let it run everything else
      return self.inner(dict(scope, user=user))


      What query do I need to do? I don't know anything about that user, in fact its anonymous.



      Help me, please.










      share|improve this question















      How to write custom authentication of user, that connects to chat over ws:// protocol? This user is on the other side of Django app, he is the mobile user, connecting websocket via ws:// from mobile app. I tried to test websocket with chrome extenshion, it couldn't connect to my websocket. I think it was because of authentication.



      In Django channels docs it says:




      If you have a custom authentication scheme, you can write a custom middleware to parse the details and put a user object (or whatever other object you need) into your scope.Middleware is written as a callable that takes an ASGI application and wraps it to return another ASGI application. Most authentication can just be done on the scope, so all you need to do is override the initial constructor that takes a scope, rather than the event-running coroutine.
      Here’s a simple example of a middleware that just takes a user ID out of the query string and uses that:
      The same principles can be applied to authenticate over non-HTTP protocols; for example, you might want to use someone’s chat username from a chat protocol to turn it into a user.




      from django.db import close_old_connections

      class QueryAuthMiddleware:
      def __init__(self, inner):
      # Store the ASGI application we were passed
      self.inner = inner

      def __call__(self, scope):
      # Look up user from query string (you should also do things like
      # check it's a valid user ID, or if scope["user"] is already populated)
      user = User.objects.get(id=int(scope["query_string"]))
      close_old_connections()
      # Return the inner application directly and let it run everything else
      return self.inner(dict(scope, user=user))


      What query do I need to do? I don't know anything about that user, in fact its anonymous.



      Help me, please.







      django authentication channels






      share|improve this question















      share|improve this question













      share|improve this question




      share|improve this question








      edited Nov 11 at 19:00









      ostcar

      763




      763










      asked Nov 7 at 19:20









      Николай

      112




      112
























          1 Answer
          1






          active

          oldest

          votes

















          up vote
          0
          down vote













          In this example code, you probably have to open the websocket connection with:



          ws://SERVER:PORT/PATH?1



          Everything after the ? is the query string. In your example code, your query_string has to be a user id, so for example 1.



          You could change the code to use different query strings. For example you could use:



          from urllib.parse import parse_qs
          from django.db import close_old_connections

          class QueryAuthMiddleware:
          def __init__(self, inner):
          # Store the ASGI application we were passed
          self.inner = inner

          def __call__(self, scope):
          # Look up user from query string (you should also do things like
          # check it's a valid user ID, or if scope["user"] is already populated)

          query_string = parse_qs(self.scope['query_string'])
          if b'user_id' in query_string:
          user = User.objects.get(id=int(query_string[b'user_id'][0]))
          close_old_connections()
          else:
          user = AnonymousUser
          # Return the inner application directly and let it run everything else
          return self.inner(dict(scope, user=user))


          Now, you can use this uri:



          ws://SERVER:PORT/PATH?user_id=1



          You sill have to make sure, that the user with the ID exists in the database. You also have to write actual auth code. Every user can connect to this application with a arbitrary user id. There is no password or auth-token required.






          share|improve this answer





















            Your Answer






            StackExchange.ifUsing("editor", function () {
            StackExchange.using("externalEditor", function () {
            StackExchange.using("snippets", function () {
            StackExchange.snippets.init();
            });
            });
            }, "code-snippets");

            StackExchange.ready(function() {
            var channelOptions = {
            tags: "".split(" "),
            id: "1"
            };
            initTagRenderer("".split(" "), "".split(" "), channelOptions);

            StackExchange.using("externalEditor", function() {
            // Have to fire editor after snippets, if snippets enabled
            if (StackExchange.settings.snippets.snippetsEnabled) {
            StackExchange.using("snippets", function() {
            createEditor();
            });
            }
            else {
            createEditor();
            }
            });

            function createEditor() {
            StackExchange.prepareEditor({
            heartbeatType: 'answer',
            convertImagesToLinks: true,
            noModals: true,
            showLowRepImageUploadWarning: true,
            reputationToPostImages: 10,
            bindNavPrevention: true,
            postfix: "",
            imageUploader: {
            brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
            contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
            allowUrls: true
            },
            onDemand: true,
            discardSelector: ".discard-answer"
            ,immediatelyShowMarkdownHelp:true
            });


            }
            });














             

            draft saved


            draft discarded


















            StackExchange.ready(
            function () {
            StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53196346%2funderstanding-django-channels-queryauthmiddleware%23new-answer', 'question_page');
            }
            );

            Post as a guest















            Required, but never shown

























            1 Answer
            1






            active

            oldest

            votes








            1 Answer
            1






            active

            oldest

            votes









            active

            oldest

            votes






            active

            oldest

            votes








            up vote
            0
            down vote













            In this example code, you probably have to open the websocket connection with:



            ws://SERVER:PORT/PATH?1



            Everything after the ? is the query string. In your example code, your query_string has to be a user id, so for example 1.



            You could change the code to use different query strings. For example you could use:



            from urllib.parse import parse_qs
            from django.db import close_old_connections

            class QueryAuthMiddleware:
            def __init__(self, inner):
            # Store the ASGI application we were passed
            self.inner = inner

            def __call__(self, scope):
            # Look up user from query string (you should also do things like
            # check it's a valid user ID, or if scope["user"] is already populated)

            query_string = parse_qs(self.scope['query_string'])
            if b'user_id' in query_string:
            user = User.objects.get(id=int(query_string[b'user_id'][0]))
            close_old_connections()
            else:
            user = AnonymousUser
            # Return the inner application directly and let it run everything else
            return self.inner(dict(scope, user=user))


            Now, you can use this uri:



            ws://SERVER:PORT/PATH?user_id=1



            You sill have to make sure, that the user with the ID exists in the database. You also have to write actual auth code. Every user can connect to this application with a arbitrary user id. There is no password or auth-token required.






            share|improve this answer

























              up vote
              0
              down vote













              In this example code, you probably have to open the websocket connection with:



              ws://SERVER:PORT/PATH?1



              Everything after the ? is the query string. In your example code, your query_string has to be a user id, so for example 1.



              You could change the code to use different query strings. For example you could use:



              from urllib.parse import parse_qs
              from django.db import close_old_connections

              class QueryAuthMiddleware:
              def __init__(self, inner):
              # Store the ASGI application we were passed
              self.inner = inner

              def __call__(self, scope):
              # Look up user from query string (you should also do things like
              # check it's a valid user ID, or if scope["user"] is already populated)

              query_string = parse_qs(self.scope['query_string'])
              if b'user_id' in query_string:
              user = User.objects.get(id=int(query_string[b'user_id'][0]))
              close_old_connections()
              else:
              user = AnonymousUser
              # Return the inner application directly and let it run everything else
              return self.inner(dict(scope, user=user))


              Now, you can use this uri:



              ws://SERVER:PORT/PATH?user_id=1



              You sill have to make sure, that the user with the ID exists in the database. You also have to write actual auth code. Every user can connect to this application with a arbitrary user id. There is no password or auth-token required.






              share|improve this answer























                up vote
                0
                down vote










                up vote
                0
                down vote









                In this example code, you probably have to open the websocket connection with:



                ws://SERVER:PORT/PATH?1



                Everything after the ? is the query string. In your example code, your query_string has to be a user id, so for example 1.



                You could change the code to use different query strings. For example you could use:



                from urllib.parse import parse_qs
                from django.db import close_old_connections

                class QueryAuthMiddleware:
                def __init__(self, inner):
                # Store the ASGI application we were passed
                self.inner = inner

                def __call__(self, scope):
                # Look up user from query string (you should also do things like
                # check it's a valid user ID, or if scope["user"] is already populated)

                query_string = parse_qs(self.scope['query_string'])
                if b'user_id' in query_string:
                user = User.objects.get(id=int(query_string[b'user_id'][0]))
                close_old_connections()
                else:
                user = AnonymousUser
                # Return the inner application directly and let it run everything else
                return self.inner(dict(scope, user=user))


                Now, you can use this uri:



                ws://SERVER:PORT/PATH?user_id=1



                You sill have to make sure, that the user with the ID exists in the database. You also have to write actual auth code. Every user can connect to this application with a arbitrary user id. There is no password or auth-token required.






                share|improve this answer












                In this example code, you probably have to open the websocket connection with:



                ws://SERVER:PORT/PATH?1



                Everything after the ? is the query string. In your example code, your query_string has to be a user id, so for example 1.



                You could change the code to use different query strings. For example you could use:



                from urllib.parse import parse_qs
                from django.db import close_old_connections

                class QueryAuthMiddleware:
                def __init__(self, inner):
                # Store the ASGI application we were passed
                self.inner = inner

                def __call__(self, scope):
                # Look up user from query string (you should also do things like
                # check it's a valid user ID, or if scope["user"] is already populated)

                query_string = parse_qs(self.scope['query_string'])
                if b'user_id' in query_string:
                user = User.objects.get(id=int(query_string[b'user_id'][0]))
                close_old_connections()
                else:
                user = AnonymousUser
                # Return the inner application directly and let it run everything else
                return self.inner(dict(scope, user=user))


                Now, you can use this uri:



                ws://SERVER:PORT/PATH?user_id=1



                You sill have to make sure, that the user with the ID exists in the database. You also have to write actual auth code. Every user can connect to this application with a arbitrary user id. There is no password or auth-token required.







                share|improve this answer












                share|improve this answer



                share|improve this answer










                answered Nov 11 at 13:31









                ostcar

                763




                763






























                     

                    draft saved


                    draft discarded



















































                     


                    draft saved


                    draft discarded














                    StackExchange.ready(
                    function () {
                    StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53196346%2funderstanding-django-channels-queryauthmiddleware%23new-answer', 'question_page');
                    }
                    );

                    Post as a guest















                    Required, but never shown





















































                    Required, but never shown














                    Required, but never shown












                    Required, but never shown







                    Required, but never shown

































                    Required, but never shown














                    Required, but never shown












                    Required, but never shown







                    Required, but never shown







                    這個網誌中的熱門文章

                    Xamarin.form Move up view when keyboard appear

                    Post-Redirect-Get with Spring WebFlux and Thymeleaf

                    Anylogic : not able to use stopDelay()