josefrichter

josefrichter

Stream pagination and subscribe/unsubscribe to individual items

Hi,

I am paginating through a bunch of classes, displaying 10 at a time. Every time I change a page, I need to subscribe to the new classes count, and unsubscribe from those shown previously. (I want the count to live-update in the table, so I will be re-inserting the classes to the stream when update is broadcast)

The only thing I was able to make work is

unsubscribe (kinda workaround)>

Sorted.PubSub
    |> Registry.keys(self())
    |> Enum.map(fn topic ->
      Phoenix.PubSub.unsubscribe(Sorted.PubSub, topic)
    end)

and subscribe>

class_ids =
        socket.assigns.streams.classes.inserts
        # Convert stream to list eagerly
        |> Enum.to_list()
        # Extract IDs
        |> Enum.map(fn {_dom_id, _, class, _} -> class.id end)

      class_ids |> Enum.each(&Sorted.Pubsub.subscribe_class_count/1)

It works, but it kinda smells to me…

I was hoping I could do something like this for both unsubscribe and subscribe

for {_dom_id, class} <- socket.assigns.streams.classes do
        Sorted.Pubsub.subscribe_class(class.id)
      end

but this is throwing

** (ArgumentError) streams can only be consumed directly by a for comprehension.
If you are attempting to consume the stream ahead of time, such as with
`Enum.with_index(@streams.classes)`, you need to place the relevant information
within the stream items instead.

On top of that, even with the above subscribe code, I was not able to unsubscribe before changing the page, as the list was always empty…

So what’s the proper way to go about this? Thank you very much.

Most Liked

codeanpeace

codeanpeace

My rule of thumb for streams is large collections that are ideally more “static” in nature and don’t require too much intricate interaction with the server. It’s especially great for collections that keep on growing over time – logs, users in chatroom, etc. If you’re only displaying 10 at a time, streams may be overkill since it does add some complexity while reducing memory usage.

That said, bouncing off of what @LostKobrakai said, you could also track the bare minimum necessary for pubsub subscribe/unsubscribe as an assign e.g. current_class_ids and use that instead of reaching into the registry and streams. ¯\_(ツ)_/¯

Schultzer

Schultzer

Making your subscription to granular can be problematic for several reasons, my thumb rule for building a complex real-time database management for Ecto is to subscribe to a table.

I should have made it clear, that I use stream, pubsub, counting and updating rows, logs etc.

Where Next?

Popular in Questions Top

sergio
In Ruby, I can go: User.find_by(email: "foobar@email.com").update(email: "hello@email.com") How can I do something similar in Elixir? ...
New
dotdotdotPaul
Okay, I'm having a heck of a time trying to figure out how to best handle the validation of belongs_to associations in Ecto. I'm sure I'...
New
freewebwithme
Using vs code and installed ElixirLS: support and debugger. And I got an error popped up on start up says Failed to run ‘elixir’ comma...
New
gonzofish
I’m currently trying to understand how to join three tables using Ecto. All the examples I’ve seen use 2, so maybe I’m just missing somet...
New
shahryarjb
Hello, I have map which I want to convert it to string like this: the map: %{last_name: "tavakkoli", name: "shahryar"} the string I ne...
New
baxterw3b
Hi guys, i’m new in the Elixir world, and i have to say, that i love it! i’m having some problem to understand anonymous functions with ...
New
wernerlaude
In AR this is so simple @articles = current_user.articles How to do in Ecto? def index(conn, _params) do current_user = conn.assig...
New
skosch
To my knowledge, put_in, Map.update etc. all have the one limitation of not automatically creating intermediate keys when needed (for exa...
New
jay1
Why is it that the mnesia database isn’t the most preferred database for use in Elixir/Phoenix?
New
joeerl
Hello again - after a longish gap I’ve decided I really must dig into Elixir and see what’s been happening here - so I have a few questio...
New

Other popular topics Top

shahryarjb
Hello, I get Persian date from my client and convert it to normal calendar like this: def jalali_string_to_miladi_english_number(persi...
New
sergio
In Ruby, I can go: User.find_by(email: "foobar@email.com").update(email: "hello@email.com") How can I do something similar in Elixir? ...
New
openscript
Hello! Sorry for this astonishing simple question, but I’m really stuck. I try to set up the intellij-elixir plugin, but I don’t know ho...
New
itssasanka
Hi all, Trying to get some more clarity over utc_datetime and naive_datetime for Ecto: https://hexdocs.pm/ecto/Ecto.Schema.html#module-...
New
axelson
This post is a wiki (feel free to hit the edit button near the bottom right of this post to add your own changes!) This post collects co...
239 45766 226
New
SoCreat
i’m a new one to elixir which editor can i use vs code? or atom? Thanks! :smiley:
New
mgjohns61585
Could someone help me? I'm making my first elixir program, number guessing game. I can't figure out how to convert the user's guess from ...
New
msaraiva
Surface is an experimental library built on top of Phoenix LiveView and its new LiveComponent API that aims to provide a more declarative...
564 42633 214
New
Qqwy
Original source of discussion: This topic on the Pragmatic Programmers' Functional Web Development with Elixir, OTP, and Phoenix forum. ...
New
AstonJ
We’ve put together this wiki for Phoenix LiveView - please feel free to add any info you feel is worth including. What is Phoenix LiveV...
New

We're in Beta

About us Mission Statement