Assume that the table name is table1
and it have primary key expression (id)
.
- We create a table which will store
id
values for rows which were inserted, updated or deleted, and also store the action type.
CREATE TABLE log (
id INT PRIMARY KEY,
action CHAR(1)
);
- We create triggers which save the info about altered rows into this table.
CREATE TRIGGER tr_ai_log
AFTER INSERT ON table1
FOR EACH ROW
REPLACE INTO log (id, action) VALUES (NEW.id, 'I');
CREATE TRIGGER tr_au_log
AFTER UPDATE ON table1
FOR EACH ROW
REPLACE INTO log (id, action) VALUES (NEW.id, 'U');
CREATE TRIGGER tr_ad_log
AFTER DELETE ON table1
FOR EACH ROW
REPLACE INTO log (id, action) VALUES (OLD.id, 'D');
These triggers stores only the most last action for each altered row. If the record for some row exists then it will be overwritten.
Now we may create new table structure and copy the data into it.
When the copy is ready for to replace old table we must:
a. Disable external access to the server.
b. Drop all external links properties (foreign keys, triggers, permissions) from old table.
c. Rename old table.
d. Rename new table.
e. Copy those rows which are listed in log
table with 'I' or 'U' action from old renamed table to new table overwriting existing one.
f. Delete rows which are listed in log
table with 'D' action from old renamed table.
g. Restore all external links properties.
- We may restore access to the server.
Create the structure for new table with caution. Especially - check charsets and collations for string-type data, if they differs then direct copy may cause in data damage. In some cases these damages are rare ("spitting into the data") and cannot be detected immediately with visual checking.