Operação única de "troca"...
TROCAR(@old_pos, @new_pos)
UPDATE
my_table
SET
position = CASE WHEN position = @old_pos THEN @new_pos ELSE @old_pos END
WHERE
position IN (@old_pos, @new_pos)
Isso não se expande facilmente para uma tabela de operações de troca. Isso porque ele tentará fazer todas as trocas de uma vez, quando na verdade as trocas devem acontecer em uma ordem específica...
Além disso, se você quiser fazer SWAP(@id, @new_pos), você precisa fazer uma subconsulta ou auto-junção na tabela que você está atualizando. O MySQL não gosta disso e, embora existam maneiras de contornar a limitação, isso torna as coisas um pouco confusas ...
UPDATE
my_table
INNER JOIN
(SELECT position AS old_pos, @new_pos AS new_pos FROM (SELECT position FROM my_table WHERE id = @id)) AS params
ON my_table.position IN (params.old_pos, params.new_pos)
SET
myTable.position = CASE WHEN position = old_pos THEN new_pos ELSE old_pos END
(Eu acho isso vai funcionar)
OBSERVAÇÃO:
Ambos assumem que AMBOS @old_pos e @new_pos, ou @id e @new_pos são encontrados, ele não verifica e irá fazer uma bagunça se eles não existirem.
Isso pode ser resolvido colocando-o em uma transação e revertendo se ROW_COUNT() mostrar que apenas 1 registro foi atualizado.