656 Stimmen

MySQL-Fehler #1071 - Der angegebene Schlüssel war zu lang; die maximale Schlüssellänge beträgt 767 Bytes

Wenn ich den folgenden Befehl ausführe:

ALTER TABLE `mytable` ADD UNIQUE (
`column1` ,
`column2`
);

Ich habe diese Fehlermeldung erhalten:

#1071 - Specified key was too long; max key length is 767 bytes

Informationen über Spalte1 und Spalte2:

column1 varchar(20) utf8_general_ci
column2  varchar(500) utf8_general_ci

でしょう varchar(20) benötigt nur 21 Bytes, während varchar(500) benötigt nur 501 Bytes. Die Gesamtzahl der Bytes beträgt also 522, also weniger als 767. Warum habe ich dann die Fehlermeldung erhalten?

#1071 - Specified key was too long; max key length is 767 bytes

5 Stimmen

Da es sich nicht um 520 Bytes, sondern um 2080 Bytes handelt, die weit über 767 Bytes hinausgehen, könnten Sie Spalte1 varchar(20) und Spalte2 varchar(170) verwenden. Wenn Sie eine Zeichen/Byte-Entsprechung wünschen, verwenden Sie latin1

3 Stimmen

Ich denke, Ihre Berechnung ist ein bisschen falsch hier. mysql verwendet 1 oder 2 zusätzliche Bytes, um die Werte Länge aufzeichnen: 1 Byte, wenn die maximale Länge der Spalte 255 Bytes oder weniger ist, 2, wenn es länger als 255 Bytes ist. die utf8_general_ci Codierung benötigt 3 Bytes pro Zeichen so varchar (20) verwendet 61 Bytes, varchar (500) verwendet 1502 Bytes insgesamt 1563 Bytes

3 Stimmen

Mysql> select maxlen, character_set_name from information_schema.character_sets where character_set_name in('latin1', 'utf8', 'utf8mb4'); maxlen | character_set_name ------ | ------------------- 1 | latin1 ------ | ------------------- 3 | utf8 ------ | ------------------- 4 | utf8mb4

15voto

maknz Punkte 3576

Wir stießen auf dieses Problem, als wir versuchten, einen UNIQUE-Index zu einem VARCHAR(255)-Feld mit utf8mb4 hinzuzufügen. Obwohl das Problem hier bereits gut beschrieben ist, wollte ich einige praktische Ratschläge hinzufügen, wie wir das Problem herausgefunden und gelöst haben.

Bei der Verwendung von utf8mb4 zählen die Zeichen als 4 Byte, während sie unter utf8 als 3 Byte gezählt werden können. InnoDB-Datenbanken können Indizes nur 767 Bytes enthalten. Bei Verwendung von utf8 können Sie also 255 Zeichen speichern (767/3 = 255), bei Verwendung von utf8mb4 jedoch nur 191 Zeichen (767/4 = 191).

Sie sind durchaus in der Lage, reguläre Indizes für VARCHAR(255) Felder mit utf8mb4, aber die Indexgröße wird automatisch bei 191 Zeichen abgeschnitten - wie unique_key hier:

Sequel Pro screenshot showing index truncated at 191 characters

Das ist in Ordnung, denn reguläre Indizes dienen nur dazu, dass MySQL Ihre Daten schneller durchsuchen kann. Das gesamte Feld muss nicht indiziert werden.

Warum schneidet MySQL den Index bei regulären Indizes automatisch ab, gibt aber einen expliziten Fehler aus, wenn dies bei eindeutigen Indizes versucht wird? Damit MySQL in der Lage ist, herauszufinden, ob der eingefügte oder aktualisierte Wert bereits existiert, muss er tatsächlich den gesamten Wert indizieren und nicht nur einen Teil davon.

Wenn Sie einen eindeutigen Index für ein Feld haben wollen, muss der gesamte Inhalt des Feldes in den Index passen. Für utf8mb4 bedeutet dies, dass Sie die Länge Ihrer VARCHAR-Felder auf 191 Zeichen oder weniger reduzieren müssen. Wenn Sie utf8mb4 für diese Tabelle oder dieses Feld nicht benötigen, können Sie es auf utf8 zurücksetzen und Ihre 255 langen Felder beibehalten.

14voto

Châu Hồng Lĩnh Punkte 1960

Hier ist meine ursprüngliche Antwort:

Ich lösche einfach die Datenbank und erstelle sie neu, und der Fehler ist verschwunden:

drop database if exists rhodes; create database rhodes default CHARACTER set utf8 default COLLATE utf8_general_ci;

Allerdings funktioniert das nicht in allen Fällen.

Es ist eigentlich ein Problem der Verwendung von Indizes auf VARCHAR-Spalten mit dem Zeichensatz utf8 (oder utf8mb4 ), mit VARCHAR-Spalten, die mehr als eine bestimmte Länge von Zeichen haben. Im Fall von utf8mb4 dass eine bestimmte Länge 191 beträgt.

Weitere Informationen zur Verwendung langer Indizes in MySQL-Datenbanken finden Sie im Abschnitt "Langer Index" in diesem Artikel: http://hanoian.com/content/index.php/24-automate-the-converting-a-mysql-database-character-set-to-utf8mb4

0 Stimmen

Das Problem mit der Einrichtung von Openmeetings ist gelöst (Sie haben mir übrigens die Nacht gerettet :-)

10voto

Nick Pridorozhko Punkte 413

Um das zu beheben, funktioniert dies für mich wie ein Zauber.

ALTER DATABASE dbname CHARACTER SET utf8 COLLATE utf8_general_ci;

0 Stimmen

Ich kann bestätigen, dass mein Problem auch mit der Datenbanksortierung zusammenhängt. Ich habe keine Erklärung dafür. Ich verwende mysql v5.6.32 und DB-Kollation war utf8mb4_unicode_ci.

0 Stimmen

Versuchen Sie, mit phpmyadmin zu erklären, siehe i.imgur.com/fJzm4oE.png

8voto

Abhishek Punkte 3298

Ich habe einige Recherchen zu diesem Thema durchgeführt und schließlich einige benutzerdefinierte Änderungen erhalten

Für MySQL Workbench 6.3.7 Version ist eine grafische Zwischenphase verfügbar

  1. Starten Sie Workbench und wählen Sie die Verbindung aus.
  2. Gehen Sie zu Management oder Instance und wählen Sie Options File.
  3. Wenn Workbench Sie nach der Erlaubnis fragt, die Konfigurationsdatei zu lesen, dann erlauben Sie es, indem Sie zweimal OK drücken.
  4. An zentraler Stelle erscheint das Fenster Administratoroptionen.
  5. Gehen Sie auf die Registerkarte InnoDB und aktivieren Sie innodb_large_prefix, wenn es nicht im Abschnitt General aktiviert ist.
  6. den Wert der Option innodb_default_row_format auf DYNAMIC setzen.

Für Versionen unter 6.3.7 sind keine direkten Optionen verfügbar, so dass Sie die Eingabeaufforderung verwenden müssen

  1. Starten Sie CMD als Administrator.
  2. Gehen Sie zum Verzeichnis, in dem der mysql-Server installiert ist. " C:\Program Dateien \MySQL\MySQL Server 5.7 \bin "Der Befehl lautet also "cd \" "cd Programmdateien \MySQL\MySQL Server 5.7 \bin ".
  3. Führen Sie nun den Befehl mysql -u Benutzername -p databasescheema Jetzt wird nach dem Passwort des jeweiligen Benutzers gefragt. Geben Sie das Passwort ein und geben Sie es in die mysql-Eingabeaufforderung ein.
  4. Wir müssen einige globale Einstellungen vornehmen, indem wir die folgenden Befehle nacheinander eingeben set global innodb_large_prefix=on; set global innodb_file_format=barracuda; set global innodb_file_per_table=true;
  5. Zu guter Letzt müssen wir das ROW_FORMAT der gewünschten Tabelle ändern. Standardmäßig ist es COMPACT, wir müssen es auf DYNAMIC setzen.
  6. Verwenden Sie folgenden Befehl alter table table_name ROW_FORMAT=DYNAMIC;
  7. Erledigt

0 Stimmen

Ich kann das nicht finden: 6. Setzen Sie den Wert der Option innodb_default_row_format auf DYNAMIC.

0 Stimmen

Wenn ich set global innodb_default_row_format = DYNAMIC; Ich sehe diese Meldung: ERROR 1193 (HY000): Unbekannte Systemvariable 'innodb_default_row_format'

0 Stimmen

Wie haben Sie den Fehler von der Workbench zu cmd bekommen? Ich habe es von der Workbench aus gemacht, die die Option direkt hat.

7voto

Mayank Dudakiya Punkte 3212

Indexlängen und MySQL / MariaDB


Laravel verwendet die utf8mb4-Zeichen standardmäßig eingestellt, was die Unterstützung für die Speicherung von "Emojis" in der Datenbank. Wenn Sie eine ältere MySQL-Version als 5.7.7 oder eine ältere MariaDB-Version als 10.2.2 verwenden, müssen Sie möglicherweise die Standard-Stringlänge, die von Migrationen generiert wird, manuell konfigurieren, damit MySQL Indizes für sie erstellen kann. Sie können dies konfigurieren, indem Sie die Schema::defaultStringLength Methode innerhalb Ihrer AppServiceProvider:

use Illuminate\Support\Facades\Schema;

/**
 * Bootstrap any application services.
 *
 * @return void
 */
public function boot()
{
    Schema::defaultStringLength(191);
}

Alternativ dazu, können Sie die Option innodb_large_prefix für Ihre Datenbank aktivieren. In der Dokumentation Ihrer Datenbank finden Sie Anweisungen, wie Sie diese Option richtig aktivieren.

Referenz aus dem Blog : https://www.scratchcode.io/specified-key-too-long-error-in-laravel/

Referenz aus der offiziellen laravel-Dokumentation : https://laravel.com/docs/5.7/migrations

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X