brendon / acts_as_list

An ActiveRecord plugin for managing lists.
http://brendon.github.io/acts_as_list/
MIT License
2.05k stars 356 forks source link

[Question] Keep position nil for a specific scope #379

Closed markoj3s closed 4 years ago

markoj3s commented 4 years ago

Hi,

Is there any clean way to keep position nil for a specific scope ?

In my case, I am implementing a system of attendance with a waiting list. I just have an Attendance table with a flag to know if the user is in the waiting list or not. And for those users with the waiting list flag ON only I would like to set up the position/priority.

Thanks, Marko

brendon commented 4 years ago

Hi @markoj3s, it's largely undocumented but you can pass hashes in the scope array:

acts_as_list scope: [:parent_id, {waiting: true}]

Have a go at something like that and let me know how you get on.

brendon commented 4 years ago

I should add a link to the code: https://github.com/brendon/acts_as_list/blob/master/lib/acts_as_list/active_record/acts/scope_method_definer.rb#L28

markoj3s commented 4 years ago

Hi @brendon ,

Thank you always for your prompt replies.

I have actually tried passing a hash after having seen below part of the documentation

class TodoItem < ActiveRecord::Base
  acts_as_list scope: [:kind, :owner_id, deleted_at: nil]
end

which made me thing that perhaps by passing the flag as a hash, it would ignore everything else, but does not seem to be the case. Because of that, I thought that maybe I was mis-using the option or that I misunderstood it.

When I save my first record with the waiting flag false, the position will be set a 1.

Please note that, I am saving the record as below (I think it should not impacts the callbacks)

@child = @parent.childs.build(<some parameters>)
@child.attendance_type = <attending value>
@child.waiting = true
@child.save!

P.S.: I am using acts_as_list (0.9.19)

brendon commented 4 years ago

Thanks @markoj3s :)

I think you're right, a position will always be applied, though I'd suspect that every item you add with a waiting: false will have position = 1? Give that a test to see.

You could just ignore the position for waiting = true records, or there is the option to not place an item in a list by default on create: https://github.com/brendon/acts_as_list/blob/master/lib/acts_as_list/active_record/acts/list.rb#L17

Your scope could just be like [:owner_id, :waiting] and that would just create two groups (Within each owner), one for waiting = true and one for false. Again you could ignore the true group's positioning?

markoj3s commented 4 years ago

Hi @brendon

Ah yeah, you are right, position 1 will always be applied for records that are not in the scope. Indeed, I can just ignore those records out of the scope, it's not a big deal.

or there is the option to not place an item in a list by default on create

This was actually to me the cleanest solution and already tried to apply it, but unfortunately, it seems like I cannot apply that option conditionally ?

If above cannot be set conditionally, then I will just go for ignoring position 1 on records that are out of the scope :)

Thank you !

brendon commented 4 years ago

Yes I think it's not a conditional option. You'd always need to add the item to the list. I think the first option of just ignoring the position on out-of-scope items is the best way to go :)

markoj3s commented 4 years ago

Okay, I will then go for that option. Thank you !