Dieser Artikel führt Sie hauptsächlich in die richtige Methode der Verschlüsselung und Entschlüsselung mit AES_ENCRYPT() und AES_DECRYPT() in MySQL ein. Die Funktion AES_ENCRYPT('password','key') in MySQL kann Feldwerte verschlüsseln Name, 'Schlüssel') Funktionsentschlüsselungsverarbeitung, der Artikel enthält detaillierte Beispielcodes, Freunde in Not können darauf verweisen, ich hoffe, es kann jedem helfen.
Vorwort
Ich bin kürzlich bei der Arbeit auf eine Anforderung wie diese gestoßen: Ich muss die Funktion AES_ENCRYPT()
verwenden, um den Klartext zu verschlüsseln und zu speichern Es ist in MySQL verfügbar, es sind jedoch einige Probleme aufgetreten ... Lassen Sie uns es unten im Detail vorstellen.
Es heißt, dass der verschlüsselte Chiffretext nach der Entschlüsselung NULL sein wird.
Sah sich die Tabellenstruktur an, die sie gesendet hatte:
Nachdem sie sich die Struktur angesehen hatte, verschlüsselte sie eine mit der Funktionszeichenfolge AES_DECRYPT() , und fügen Sie es dann ein. Nach erfolgreicher Ausführung wird ein warning:<br>Query OK, 1 row affected, 1 warning (0.00 sec)
angezeigt (es wird kein Fehler, sondern eine Warnung gemeldet, wahrscheinlich aufgrund von sql_mode)
Zu diesem Zeitpunkt , sie ignoriert Nachdem ich diese Warnung gehört und mit AES_DECRYPT()
entschlüsselt hatte, stellte ich fest, dass der herausgenommene Klartext NULL war.
Beim Rückblick auf die Tabellenstruktur haben wir festgestellt, dass das Feldattribut „varchar“ && und der Zeichensatz ut8 ist. Die Warnung lautet wie folgt:
mysql> show warnings; +---------+------+------------------------------------------------------------------------+ | Level | Code | Message | +---------+------+------------------------------------------------------------------------+ | Warning | 1366 | Incorrect string value: '\xE3f767\x12...' for column 'passwd' at row 1 | +---------+------+------------------------------------------------------------------------+ 1 row in set (0.00 sec)
Überprüfen Sie die Dokumentation und werfen Sie einen Blick auf die Verwendung dieser beiden Funktionen:
-- 将'hello world'加密,密钥为'key',加密后的串存在@pass中 mysql> SET @pass=AES_ENCRYPT('hello world', 'key'); Query OK, 0 rows affected (0.00 sec) -- 看一下加密后串的长度(都为2的整数次方) mysql> SELECT CHAR_LENGTH(@pass); +--------------------+ | CHAR_LENGTH(@pass) | +--------------------+ | 16 | +--------------------+ 1 row in set (0.00 sec) -- 使用AES_DECRYPT()解密 mysql> SELECT AES_DECRYPT(@pass, 'key'); +---------------------------+ | AES_DECRYPT(@pass, 'key') | +---------------------------+ | hello world | +---------------------------+ 1 row in set (0.00 sec)
Wie speichert man es also?
Methode ①:
Setzen Sie die Feldattribute auf varbinary/binary/vier Blob-Typen und andere binäre Feldattribute.
Erstellen Sie drei Felder mit den Attributen „varbinary“, „binary“ und „blob“.
Verschlüsseln Sie „plaintext1“, „text2“, „plaintext_text3“ mit dem Schlüssel und speichern Sie sie in der Tabelle.
Nehmen Sie es zuletzt heraus.
mysql> CREATE TABLE t_passwd (pass1 varbinary(16), pass2 binary(16), pass3 blob); Query OK, 0 rows affected (0.00 sec) mysql> INSERT INTO t_passwd VALUES (AES_ENCRYPT('明文1', 'key'), AES_ENCRYPT('text2', 'key'), AES_ENCRYPT('明文_text3', 'key')); Query OK, 1 row affected (0.01 sec) mysql> SELECT AES_DECRYPT(pass1, 'key'), AES_DECRYPT(pass2, 'key'), AES_DECRYPT(pass3, 'key') FROM t_passwd; +---------------------------+---------------------------+---------------------------+ | AES_DECRYPT(pass1, 'key') | AES_DECRYPT(pass2, 'key') | AES_DECRYPT(pass3, 'key') | +---------------------------+---------------------------+---------------------------+ | 明文1 | text2 | 明文_text3 | +---------------------------+---------------------------+---------------------------+ 1 row in set (0.00 sec)
Die Länge in den Attributklammern hängt natürlich von der Länge des Klartextes ab. Der Klartext ist hier kürzer, daher wird nur 16 angegeben.
Methode ②:
Hexadezimalisieren Sie den Chiffretext und speichern Sie ihn in der Spalte varchar/char.
Hier müssen Sie HEX() zum Einzahlen und UNHEX()
zum Abheben verwenden.
Erstellen Sie ein Feld mit einem String-Attribut.
Verschlüsseln Sie „Hallo Welt“ mit AES unter Verwendung des Schlüssels „key2“ und verhexen Sie dann die verschlüsselte Zeichenfolge über die HEX-Funktion.
Entnehmen Sie abschließend die verschlüsselte Zeichenfolge über UNHEX und entschlüsseln Sie sie dann über den AES-Schlüssel „key2“:
mysql> CREATE TABLE t_passwd_2(pass1 char(32)); Query OK, 0 rows affected (0.01 sec) mysql> INSERT INTO t_passwd_2 VALUES (HEX(AES_ENCRYPT('hello world', 'key2'))); Query OK, 1 row affected (0.00 sec) mysql> SELECT AES_DECRYPT(UNHEX(pass1), 'key2') FROM t_passwd_2; +-----------------------------------+ | AES_DECRYPT(UNHEX(pass1), 'key2') | +-----------------------------------+ | hello world | +-----------------------------------+ 1 row in set (0.00 sec)
In ähnlicher Weise gilt je nach Länge des Klartextes: AES_ENCRYPT-Verschlüsselung Die Länge der Zeichenfolge nach HEX ändert sich ebenfalls, sodass sich auch die Länge der Zeichenfolge nach HEX ändert.
Bei der tatsächlichen Nutzung muss ein angemessener Wert auf der Grundlage des Geschäfts ermittelt werden.
Methode ③:
wird ohne Hexadezimalkonvertierung direkt in Varchar gespeichert.
Um zum Anfang des Problems zurückzukehren: Es ist nicht möglich, die verschlüsselte Zeichenfolge im UTF8-Zeichensatz zu speichern und das Attribut ist varchar.
Ändern Sie einfach den Zeichensatz in latin1:
Die Warnung wird beim Einfügen nicht gemeldet.
mysql> CREATE TABLE t_passwd_3(pass varchar(32)) CHARSET latin1; Query OK, 0 rows affected (0.00 sec) mysql> INSERT INTO t_passwd_3 SELECT AES_ENCRYPT('text', 'key3'); Query OK, 1 row affected (0.00 sec) Records: 1 Duplicates: 0 Warnings: 0 mysql> SELECT AES_DECRYPT(pass, 'key3') FROM t_passwd_3; +---------------------------+ | AES_DECRYPT(pass, 'key3') | +---------------------------+ | text | +---------------------------+ 1 row in set (0.00 sec)
Obwohl diese Methode schön ist, muss sie nur den Feldzeichensatz auf latin1 setzen, aber sie kann versteckte Gefahren mit sich bringen:
Das Dokument sagt Folgendes: Ein Satz:
Viele Verschlüsselungs- und Komprimierungsfunktionen geben Zeichenfolgen zurück, deren Ergebnis beliebige Bytewerte enthalten kann. Wenn Sie diese Ergebnisse speichern möchten, verwenden Sie eine Spalte mit dem binären Zeichenfolgendatentyp VARBINARY oder BLOB Mögliche Probleme beim Entfernen von nachgestellten Leerzeichen oder bei der Zeichensatzkonvertierung, die Datenwerte ändern würden, wie sie beispielsweise auftreten können, wenn Sie einen nicht-binären Zeichenfolgendatentyp (CHAR, VARCHAR, TEXT) verwenden.
Das heißt, wenn Sie die verwenden Methode ③ Auf diese Weise kann das direkte Speichern der verschlüsselten Zeichenfolge im Typ char/varchar/text potenzielle Auswirkungen haben, wenn eine Zeichenkonvertierung durchgeführt wird oder Leerzeichen gelöscht werden.
Wenn es also in char/varchar/text gespeichert werden muss, dann beziehen Sie sich auf Methode ② und hexadezimalisieren Sie es.
Oder wie bei Methode ① direkt im Binärfeld speichern.
Verwandte Empfehlungen:
Wie verwende ich OpenSSL anstelle von Mcrypt-Verschlüsselung und -Entschlüsselung in PHP?
Das obige ist der detaillierte Inhalt vonSo verwenden Sie AES_ENCRYPT() und AES_DECRYPT() korrekt zum Ver- und Entschlüsseln von MySQL. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!