I'm trying to add UUIDs to some tables in some of my MySQL databases (MySQL 5.7.9). First of all, I start by adding a column to receive the UUIDs:
ALTER TABLE `mytable` ADD COLUMN `Uuid` BINARY(16) DEFAULT NULL;
Then, for all entries that are already in the table, I generate UUIDs (since every entry in the DB will have received a NULL value in it's UUID field.
UPDATE `mytable` SET Uuid= unhex(replace(uuid(),'-','')) WHERE Uuid IS NULL;
Now, the thing is that I get some very weird behaviour by doing this; on some of my databases, every UUID generated is unique (as expected). However, on other databases, all generated UUIDs are identical (not similar, identical).
I suspect that this is due to the MySQL query optimiser, since behaviour is not consistent between different database instances (all on MySQL 5.7.9). However, I have no clue how to solve this issue.
So, MySQL gurus, am I doing something wrong?
I had the same problem, but the solution was a later answer to the linked question. I had a default character set of utf8mb4, and the theory is that it implicitly converts uuid()'s utf8 result to a constant string, before the sql executes. Converting the other parameters to utf8 avoids that:
UPDATE `mytable` SET Uuid= unhex(replace(uuid(), _utf8'-', _utf8'')) WHERE Uuid IS NULL;
The later answer links to the relevant (not a) bug report. This SO issue looks related.
The solution in the link from @TimBiegelsen works.
I declared a function to generate UUID according to v4 standard.
CREATE FUNCTION uuid_v4()
RETURNS BINARY(16)
BEGIN
-- Generate 8 2-byte strings that we will combine into a UUIDv4
SET @h1 = LPAD(HEX(FLOOR(RAND() * 0xffff)), 4, '0');
SET @h2 = LPAD(HEX(FLOOR(RAND() * 0xffff)), 4, '0');
SET @h3 = LPAD(HEX(FLOOR(RAND() * 0xffff)), 4, '0');
SET @h6 = LPAD(HEX(FLOOR(RAND() * 0xffff)), 4, '0');
SET @h7 = LPAD(HEX(FLOOR(RAND() * 0xffff)), 4, '0');
SET @h8 = LPAD(HEX(FLOOR(RAND() * 0xffff)), 4, '0');
-- 4th section will start with a 4 indicating the version
SET @h4 = CONCAT('4', LPAD(HEX(FLOOR(RAND() * 0x0fff)), 3, '0'));
-- 5th section first half-byte can only be 8, 9 A or B
SET @h5 = CONCAT(HEX(FLOOR(RAND() * 4 + 8)),
LPAD(HEX(FLOOR(RAND() * 0x0fff)), 3, '0'));
-- Build the complete UUID
RETURN UNHEX(LOWER(CONCAT(@h1, @h2, @h3, @h4, @h5, @h6, @h7, @h8)));
END;;
DELIMITER ;
Best solution is:
UPDATE mytable SET Uuid= MID(UUID(),1,36) WHERE Uuid IS NULL;
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With