web-dev-qa-db-de.com

Abfrage, um Tabellen zu finden, die in der letzten Stunde geändert wurden

Ich möchte herausfinden, welche Tabellen in der letzten Stunde in einer MySQL-Datenbank geändert wurden. Wie kann ich das machen?

30
agente_secreto

MySQL 5.x kann dies über die Datenbank INFORMATION_SCHEMA tun. Diese Datenbank enthält Informationen zu Tabellen, Ansichten, Spalten usw.

SELECT * 
FROM `INFORMATION_SCHEMA`.`TABLES`
WHERE 
    DATE_SUB(NOW(), INTERVAL 1 HOUR) < `UPDATE_TIME`

Gibt alle Tabellen zurück, die in der letzten Stunde aktualisiert wurden (UPDATE_TIME). Sie können auch nach Datenbanknamen filtern (Spalte TABLE_SCHEMA).

Eine Beispielabfrage:

SELECT 
    CONCAT(`TABLE_SCHEMA`, '.', `TABLE_NAME`) AS `Table`, 
    UPDATE_TIME AS `Updated`
FROM `INFORMATION_SCHEMA`.`TABLES`
WHERE
    DATE_SUB(NOW(), INTERVAL 3 DAY) < `UPDATE_TIME`
    AND `TABLE_SCHEMA` != 'INFORMATION_SCHEMA'
    AND `TABLE_TYPE` = 'BASE TABLE';
55
rjh

Für jede Tabelle, für die Sie Änderungen feststellen möchten, benötigen Sie eine Spalte mit dem Zeitstempel der letzten Änderung.

Für jede Einfügung oder Aktualisierung in der Tabelle müssen Sie diese Spalte mit dem aktuellen Datum und der aktuellen Uhrzeit aktualisieren.

Alternativ können Sie einen trigger einrichten, der die Spalte bei jedem Einfügen oder Ändern automatisch aktualisiert. Auf diese Weise müssen Sie nicht alle Ihre Abfrage ändern.

Wenn dies funktioniert, führen Sie die Abfrage aus, um herauszufinden, ob Zeilen aus einer Tabelle in der letzten Stunde geändert wurden

select count(*) from mytable where datemod>subtime(now(),'1:0:0')

Wiederholen Sie dies für jede Tabelle, die Sie überprüfen möchten.

5
David V.

InnoDB verfügt derzeit noch nicht über einen systemeigenen Mechanismus, um diese Informationen abzurufen. In der bezogenen Funktionsanforderung bei MySQL empfiehlt jemand, AFTER [all events]-Trigger für jede zu überwachende Tabelle festzulegen. Der Auslöser würde eine Anweisung wie ausgeben

INSERT INTO last_update VALUE ('current_table_name', NOW())
ON DUPLICATE KEY UPDATE update_time = NOW();

in einer Tabelle wie folgt:

CREATE TABLE last_update (
    table_name VARCHAR(64) PRIMARY KEY,
    update_time DATETIME
) ENGINE = MyISAM; -- no need for transactions here

Wenn eine leichte Ungenauigkeit dieser Daten (im Bereich von einer Sekunde) akzeptabel ist und Sie Lesezugriff auf die MySQL-Datendateien haben, können Sie alternativ zu einer Einstellung wechseln, in der inndb_files_per_table = ON (in jedem Fall empfohlen) und prüfen Sie die letzte Änderungszeit der zugrunde liegenden Datendateien.

Diese Dateien befinden sich in den meisten Standardinstallationen unter /var/lib/mysql/[database_name]/*.ibd.

Wenn Sie sich für diese Route entscheiden, müssen Sie vorhandene Tabellen neu erstellen , damit die neue Einstellung übernommen wird.

4
RandomSeed

Ich habe vor etwa 1,5 Jahren eine solche Frage in DBA StackExchange beantwortet: Der schnellste Weg, um zu prüfen, ob die InnoDB-Tabelle geändert wurde

Basierend auf dieser alten Antwort empfehle ich Folgendes

Flushing schreibt auf die Festplatte

Dies ist eine einmalige Einrichtung. Sie müssen innodb_max_dirty_pages_pct auf 0 setzen.

Fügen Sie dies zunächst zu /etc/my.cnf hinzu

[mysqld]
innodb_max_dirty_pages_pct=0

Führen Sie dann Folgendes aus, um einen Neustart von mysql zu vermeiden:

mysql> SET GLOBAL innodb_max_dirty_pages_pct = 0;

Timestamp der InnoDB-Tabelle .ibd file abrufen

ls hat die Option, den UNIX-Zeitstempel in Sekunden abzurufen. Für eine InnoDB-Tabelle mydb.mytable

$ cd /var/lib/mysql/mydb
$ ls -l --time-style="+%s" mytable.ibd | awk '{print $6}'

Sie können dann UNIX_TIMESTAMP (NOW ()) - (timestamp of the .ibd file) berechnen und prüfen, ob es 3600 oder weniger ist.

Versuche es !!!

3
RolandoMySQLDBA
SELECT *
FROM  information_schema.tables
WHERE UPDATE_TIME >= SYSDATE() - INTERVAL 1 DAY  && TABLE_TYPE != 'SYSTEM VIEW'

SELECT * 
FROM information_schema.tables
WHERE UPDATE_TIME >= DATE_SUB(CURDATE(), INTERVAL 1 DAY) && TABLE_TYPE != 'SYSTEM VIEW'
0
user1140237