Our application has a table called cargo_items. It can be seen as kind of a queue to later process these items. Initially there was a SINGLE job which took 3000 entries and
You will have deadlocks with this approach. You could avoid them by simply using order by id in subquery.
But it will prevent any concurrent running of this queries, as concurrent queries will always try first to mark the lowest free id, and block until the first client will commit. I don't think this is a problem if you process say less than one batch per second.
You don't need advisory locks. Avoid them if you can.