I finally solved this issue by using dynamic fields. Here's what the searchable declaration looks like:
searchable do
integer user_ids
dynamic_boolean :document_read_status do
user_ids = get_all_user_ids
unread_user_ids = get_all_unread_user_ids
user_ids.inject({}) do |hash, user_id|
hash.merge(:"unread_by_#{user_id}" => unread_user_ids.include?(user_id))
end
end
end
and the actual search looks like this:
search.build do
with(:user_ids, user.id)
dynamic :document_read_status do
order_by(:"unread_by_#{user.id}", :desc)
end
end
In case you're wondering what's with the the interpolated string as the key and why I didn't use the user id as the key directly, that answer can be found here: Indexing and ordering by dynamic field with sunspot
In case there's something wrong with this approach, any input would be welcomed.