Reorder lists in PATCH

Let’s say I have an ordered list of items and order is defined by “position” attribute stored in the database.

  • item a (position: 1)
  • item b (position: 2)
  • item c (position: 3)
  • item d (position: 4)

Now I want to reorder the list and move item d to the top

  • item d (position: 4 → 1)
  • item a (position: 1 → 2)
  • item b (position: 2 → 3)
  • item c (position: 3 → 4)

The position of all elements has changed and I would have to do a separate PATCH for every element. I don’t want to do it this way because of several reasons:

  • the list can be huge
  • some items in the list can be hidden

What I’m actually searching for is another way of ordering items where reordering could be done only by PATCHing one resource.

Closest idea I have now is ordering by pointers (where one item points to another). When reordering in this way you have to only PATCH two resources. The problem here is how to order items in the database this way…

Any ideas? :slight_smile:

What are you using for your back end? If you are using Rails, @mixonic’s ranked-model gem would enable you achieve what you describe.

I don’t think it does exactly what you describe, but you might find the ember-sortable addon helpful too.

Hey tomchen, thank you for the reply.

Yeah I use Rails in the backend.

Ranked-model is a nice idea but, correct me if I’m wrong, “several movements of items before no digits are available” can actually happen quite often. Then the list is rebalanced which could lead to inconsistent data on your frontend.

Also looks like the gem is quite old and not maintained any more.

That is a good point. I’ve been using ranked-model without issues, but it does look like it hasn’t received much love in a while. There are a number of other similar gems (acts_as_list seems to be more actively maintained) you could investigate.

You are correct though, the way ranked-model works is that if the digits run out, all of the positions on the backend would be rebalanced, but I don’t see how you can reorder an arbitrarily large number of records without eventually running into this issue. Depending on your use case and how large your data set is, it may mean that you need to reload your records on the front end periodically to keep the data in sync. Hope that helps.

I’ve been using acts_as_list up until now and it works great for a Rails powered application. And you don’t have any issues with this problem because you reload your page on every request and everything sits back into place.

But as I’m now separating Rails API and Ember app it’s kinds strange, from the API point of view, to do a PATCH of a single resource which actually updates X resources in the background.

I know I could “hack” my frontend to periodically sync the data but I’m trying to think what’s a proper way for my API to behave.