Once I have my three functions (add, remove and receive), I have to call them all in my functions connect?
Honestly I never had so much trouble on a package, sorry again for your time, I followed the doc and here is the rendering of my code
class HubriseOrderConsumer(ListModelMixin, GenericAsyncAPIConsumer):
def get_queryset(self, **kwargs):
return HubriseOrder.objects.filter(ascount=self.scope["user"]).exclude(
status='En attente').exclude(
status='Rejeter').exclude(
status='Compléter').exclude(
status='new').exclude(
status='Livraison échouer').order_by('created_at')
serializer_class = HubriseOrderSerializer
permissions = (permissions.AllowAny,)
async def connect(self, **kwargs):
await self.room_connect()
await self.receive()
await self.model_change.subscribe()
await super().connect()
async def disconnect(self, close_code):
await self.room_disconect()
@database_sync_to_async
async def room_connect(self, **kwargs):
Room.objects.add("some_room", self.channel_name, self.scope["user"])
@database_sync_to_async
async def receive(self, text_data=None, bytes_data=None):
if text_data == '"heartbeat"':
Presence.objects.touch(self.channel_name)
@database_sync_to_async
async def room_disconect(self, **kwargs):
Room.objects.remove("some_room", self.channel_name)
@model_observer(HubriseOrder)
async def model_change(self, message, observer=None, **kwargs):
await self.send_json(message)
@model_change.serializer
def model_serialize(self, instance, action, **kwargs):
return dict(data=HubriseOrderSerializer(instance=instance).data, action=action.value)
I also added the script in my html
<script>
setInterval(function() {
socket.send(JSON.stringify("heartbeat"));
}, 30000);
</script>
My websocket is connected, but no data has been sent. However I followed the documentation ![]()
No worries - it took me a long time to really wrap my head around async and Channels - and I’m still not confident I understand everything the way I should.
I just noticed something - Why do you have a super().connect() in your connect function? I don’t see any documentation saying that it’s necessary or even appropriate to do that, nor showing any examples with it in them.
Aside from the Channels tutorial, have you examined any other Channels-based projects to see how they function? I learned a lot from Andrew Godwin’s channels-examples repo. (My htmx_channels sample is available as well, but I don’t really hold it up as a great learning tool - it’s only intended to show one way of integrating htmx with Channels - and even at that it’s out-of-date and in serious need of a refresh.)
But in the documentation of django-channels-presence, it puts it as an example
super().connect() I looked at your documentation I understood some concepts but I still can’t understand with channels-django-presence, I tried to find examples that use django-channels-presence, but I can’t find any… From your experience with django-channels-presence, do you think you can guide me? (it’s the last line for me to finish this project)
Notice that that implementation of connect doesn’t do any of the other work done by a connect function.
Also, if you look at the source for WebsocketConsumer, you’ll see it’s an instance of a SyncConsumer, not an AsyncConsumer.
So the parent class is something different than what you’re using.
I’m more than happy to - that’s why I’m here.
But you’re getting to the point with this where you’re going to need to understand every individual line of code. You should be able to read a line of code, and figure out what it’s doing, and not just adding code because you see it in an example. Yes, the examples are great, and there’s nothing wrong with copy/paste-driven development - if you understand what you’re copying, and why you’re pasting it into your project.
I’m going to explain you what I understood, because I really don’t understand where the problem comes from.
room_connect is used to add a room in the database so that when a user connects, he connects to this specific room that is dedicated to him
@database_sync_to_async
async def room_connect(self, **kwargs):
Room.objects.add("some_room", self.channel_name, self.scope["user"])
receive, is used to retrieve heartbeats send from the js, to know if an active connection is not marked as obsolete
@database_sync_to_async
async def receive(self, text_data=None, bytes_data=None):
if text_data == '"heartbeat"':
Presence.objects.touch(self.channel_name)
room_disconect is just to remove the user’s room when he leaves the websoket
@database_sync_to_async
async def room_disconect(self, **kwargs):
Room.objects.remove("some_room", self.channel_name)
The rest is just to get the Serializer.
Then in my connect function, I just have to call each function
async def connect(self, **kwargs):
await self.room_connect()
await self.receive()
await self.model_change.subscribe()
This is where things are starting to go sideways.
The receive method is what receives all websocket frames from the browser, not only the heartbeats. If you go back to the Channels tutorials , Tutorial Part 2: Implement a Chat Server — Channels 4.0.0 documentation and Tutorial Part 3: Rewrite Chat Server as Asynchronous — Channels 4.0.0 documentation, you will see the examples of what their receive methods do.
Also notice in the section for Heartbeats, they show the ellipsis (...) in the receive method specifically to indicate that this example adds to your existing code and does not replace it.
Except you’re calling functions you shouldn’t call (e.g. receive) and not calling functions you should (e.g. accept). Again, go back to the tutorial and review the sample code.
Edit: You also need to reread the purpose and function of the @database_sync_to_async decorator to understand what it does and how it’s used.
But actually, I didn’t have a receiving function, so I’m not replacing anything, I’m just adding them.
if I understood correctly the receive function allows you to retrieve data sent by the client and process them accordingly, but in my case I only have the Heartbeats to process, right?
Your consumer class isn’t one of the base consumer classes. You need to check what your parent classes are supposed to be doing.
I’m sorry, I really don’t see it, I’ve been flipping through the docs for a while now, but it’s really beyond my reach.
you can tell me what is missing in my consumer directly, after I don’t know how many hours of research I have absolutely no idea where the problem comes from, I prefer that you explain to me what exactly is missing, even if it’s not a good methodology, so that next time I’ll be able to configure a web myself
I can’t, because I’m not familiar with the libraries you are using or the base classes you’re trying to build from. If you can’t understand what those classes are doing, there’s not really anything I can do to help.
About the best I could help you with is starting back from the basics to help you understand how Channels work, and what’s necessary for a base consumer.
it’s very frustrating because I don’t know what to do, there’s no example I can use that looks like what I want to do
I get that. But that’s why understanding what everything is doing is so important. You can’t build every project by just following examples.
If nothing else, you may need to take a step back to what you do understand, and then work forward from there.
And this does not mean just going back to your most recent working code if you don’t understand everything that that code is doing. You may need to go all the way back to the very first tutorial and work through it again, focusing on each line and how it contributes to the whole - adding one piece at a time until you’re ready to progress beyond that point. Then make some trivial changes to see how you might be able to enhance the functionality.
I know I’ve worked through the original Channels tutorial at least three times, and have examined Andrew’s channels-examples repo in detail twice. My little htmx demo is an example of a very small incremental improvement. Channels itself is not trivial, and async adds complexity on top of that.
I’ll do it, but the problem is that it’s a project that I need to finish as soon as possible, do you think there’s a possibility that you provide me with one of your discord or skype contacts, whatever you want so I can show you my code in more detail, even if I have to pay, I’ll pay. It’s something pretty urgent ![]()
No, I’m sorry but I cannot provide private services. If you’re looking for more specific help, I suggest you contact one of the Django shops who provide such help.
Hello @KenWhitesell , I’m writing to you just to keep you informed because you helped me a lot and in case one day someone is in the same problem as me.
Finally I configured a filter in my js, which compares the data to my current data and if the data I receive is the same as the data related to the user it pushes the data in my html to use it
my condition :
if(allData.data.location_id == "{{ HubriseData.location }}")
My entire code :
ws.onmessage = function (e) {
allData = JSON.parse(e.data);
if (allData.action === "list") {
vueApp.$data.HubriseOrder = allData.data;
vueApp.$forceUpdate();
} else if (allData.action === "update") {
} if(allData.data.location_id == "{{ HubriseData.location }}"){
console.log('test réussie')
vueApp.$data.HubriseOrder.push(allData.data);
}else{
console.log("test échouer")
}
};
Anyway, thanks a lot for your help ![]()