sql >> Databasteknik >  >> RDS >> Mysql

Undvik dödlås genom att beställa uttryckligen

Även om du kan göra det genom straight_join, kan du också explicit få låsen på de rader du vill ha genom att duplicera select ...för uppdatering på den du vill skaffa först.

CREATE TEMPORARY TABLE colorsToUpdate (
     colorID BIGINT(20) NOT NULL, 
     modelID BIGINT(20) NOT NULL
);

insert into colorsToUpdate ( colorID, modelID)
SELECT  id, model_id
FROM    colors
where id in (101, 105, 106);

#This will try to acquire lock on models
select m.* from models m
join colorsToUpdate c
on c.modelID = m.id
for UPDATE;

#this will try to get locks on models, and colors.
select m.*, c.*
from colorsToUpdate u
left join models m
on u.modelID = m.id
join colors c 
on u.colorID = c.ID
order by m.id asc, c.id asc
for update;

# do your data modification here.

drop table colorsToUpdate;

Eftersom låsningen görs i flera steg, skulle det vara möjligt för poster i tabellens "färger" att ändras mellan när du ställer in den tillfälliga tabellen och när du är klar med låsen på de två borden.

Det kan vara ok för dig (dvs. om du bara vill ändra befintliga poster, när transaktionen startar) men kan orsaka subtila buggar om det inte är vad du vill.




  1. Få ett specifikt datumintervall

  2. är det vanligt att ha miljontals tabeller och miljontals rader inom dem i MySQL-databasdesign?

  3. MySQL uppdaterar ett fält med hjälp av information i annan tabell

  4. MySQL Fulltext Stopwords motivering