Ein Bestellschema um Abholoptionen erweitern

MySQLBeginner
Jetzt üben

Einführung

Ein kleines Geschäft führt Abholstellen ein. Sein älterer Checkout übermittelt Bestell-ID, Kundenname, ganzzahlige Centbeträge und eine Notiz; ein neuer Checkout übermittelt zusätzlich einen Abholcode. Bestehende Bestellungen und ihre Artikelbeziehungen müssen nutzbar bleiben. Ein Standardwert erhält die Kompatibilität bei einer ausgelassenen Spalte, sagt uns aber nicht, wo eine historische Kundin oder ein historischer Kunde die Bestellung tatsächlich abholen wollte.

Du lieferst expand.sql und eine erweiterte aktuelle Bestelltabelle ab, verwendest beide vorbereiteten Clients und beobachtest dann die tatsächliche Grenze zwischen Datentransaktionen und MySQL-DDL. Voraussetzungen sind grundlegende Terminalnavigation sowie MySQL SELECT/WHERE, INSERT/UPDATE, Spalten, Primärschlüssel und Standardwerte. Python- oder Anwendungsentwicklung ist nicht erforderlich. Diese unabhängige Einheit stellt ihr eigenes privates Oracle MySQL und Terminal bereit; der allgemeine Datenbankdienst ist davon unabhängig.

Arbeite nur unter /home/labex/project/pickup-desk. Du darfst die dokumentierte Abholspalte zu orders hinzufügen und für die Demonstration nur das isolierte ddl_demo aktualisieren/erweitern. Bewahre alle ursprünglichen Bestell-IDs, Kunden, Beträge, Notizen, Artikel, Abholstellen und Freigabetabellen sowie die bereitgestellten Werkzeuge. Nur die drei unten benannten Übungsbestellungen dürfen hinzugefügt werden. Dies ist ein kontrolliertes Wartungsfenster, keine Online-Migration, Migration ohne Sperren oder Migration ohne Ausfallzeit. Die Zeitschätzung des Autors umfasst Lesen und gewöhnliche Fehler; sie wurde nicht mit Anfängern gemessen.

Das Schema erweitern, während beide Clients weiter funktionieren

In diesem Schritt erstellst du eine normale Bestellung mit dem alten Client, ergänzt eine kompatible Abholspalte und liest tatsächliche Bestellungen beider Clientversionen.

Beginne in Terminal an der Shell-Eingabeaufforderung. cd ändert das aktuelle Verzeichnis; der absolute Pfad funktioniert aus jedem Ausgangsverzeichnis. ./shop führt einen vorbereiteten Befehl in diesem Verzeichnis aus. Dies sind Shell-Befehle, keine Eingaben an einer MySQL-Eingabeaufforderung:

cd /home/labex/project/pickup-desk
./shop status
./shop points

Die ursprünglichen Bestellköpfe sind 101 / Sam / 2100, 102 / Sam / 3400 und 103 / Lee / 0 mit ihren eigenen Notizen und Artikeln. Die beiden Sam-Bestellungen sind unterschiedliche Identitäten. Beträge sind ganzzahlige Centwerte, und null ist gültig. status und show lesen tatsächlich gespeicherte Werte; sie migrieren niemals einen Datensatz oder ersetzen eine Abholentscheidung.

Der vorbereitete alte Client akzeptiert old order_id customer total_cents sku quantity. Er fügt einen Bestellkopf mit ausdrücklich benannten alten Spalten und einen Artikel in derselben nativen Transaktion ein. Ein erfolgreicher Aufruf bestätigt per Commit; ein nativer SQL-Fehler stoppt den Batch und schließt seine Verbindung, wodurch ausstehende Datenänderungen zurückgerollt werden. Erstelle die erlaubte gewöhnliche Bestellung und lies sie dann:

./shop old 201 Mina 1600 MUG 1
./shop show 201

Ihr Bestellkopf enthält ID 201, Mina, 1600 und Created by legacy client; ihr Detail enthält MUG, Menge 1. Das zurückgegebene pickup_column: false besagt, dass dieses Feld nicht bereitgestellt ist. Der neue Client hat dieselben Argumente, gefolgt von einem Abholcode. Der nächste Befehl soll absichtlich mit dem nativen Fehler 1054, unbekannte Spalte pickup_code, und einem Exit-Status ungleich null fehlschlagen. Er darf weder Bestellkopf noch Detail hinterlassen:

./shop new 203 Pia 1900 CARD 2 garden
./shop show 203

Der Lesezugriff zeigt leere Kopf-/Artikelergebnisse. Eine fehlende Spalte ist ein Schemafehler, kein unbekannter Abholcode und kein erfolgreicher leerer Checkout.

Ergänze die neue Spalte, die NULL zulässt, mit dem ausdrücklichen Standardwert counter. ALTER TABLE ändert eine Definition; ADD COLUMN ergänzt das Feld. VARCHAR(16) speichert einen kurzen Abholcode. NULL erlaubt in dieser Erweiterungsphase vorübergehend einen ausdrücklich unbekannten Wert. DEFAULT 'counter' liefert den Kompatibilitätswert, wenn ein alter Client die Spalte auslässt. Er erscheint nach dieser Erweiterung auch auf bereits vorhandenen Zeilen und ist daher kein Beweis einer historischen Entscheidung. Das nächste unabhängige Lab behandelt die freigegebene Historie, bevor endgültige Regeln verschärft werden.

Speichere eine vollständige SQL-Datei. cat > expand.sql ersetzt diese eine Datei. Die Here-Dokument-Markierung 'SQL' in Anführungszeichen lässt die Shell die Zeilen wörtlich bis zum abschließenden alleinstehenden SQL kopieren. Ein Semikolon beendet jede SQL-Anweisung:

cat > expand.sql <<'SQL'
ALTER TABLE orders ADD COLUMN pickup_code VARCHAR(16) NULL DEFAULT 'counter';
SQL

apply führt die gespeicherte Datei unverändert in einer nativen MySQL-Batchverbindung mit der Migrationsrolle des Kurses aus. Es leitet nichts selbst ab, trägt keine historischen Daten automatisch nach und repariert kein fehlendes SQL:

./shop apply expand.sql
./db -e "SHOW COLUMNS FROM orders;"

./db verbindet sich mit der privaten Datenbank dieses Kurses; -e führt das folgende SQL in Anführungszeichen aus und beendet sich. Die doppelten Anführungszeichen halten Leerzeichen und Semikolon innerhalb eines Shell-Arguments. Lies Typ, NULL-Zulässigkeit und Standardwert der Abholspalte: varchar(16), YES, counter. Andere ursprüngliche Felder bleiben vorhanden.

Verwende den alten Client erneut und wiederhole die zuvor abgelehnte neue Bestellung:

./shop old 202 Omar 1800 BAG 1
./shop new 203 Pia 1900 CARD 2 garden
./shop show 201
./shop show 202
./shop show 203
./shop status

Bestellungen 201 und 202 enthalten den tatsächlich gespeicherten Standardwert counter; 203 enthält garden. Alle Bestellköpfe und tatsächlichen Artikelzeilen bleiben erhalten. Die ursprünglichen drei Bestellungen zeigen nun counter als Erweiterungsstandard; behaupte nicht, dass jede historische Bestellung dort abgeholt wurde. Die vorbereitete Freigabezuordnung bleibt unberührt.

Führe bei einem gewöhnlichen Tippfehler ./shopp zuerst ls aus und verwende ./shop mit dem korrekten Namen. Meldet SQL einen Syntaxfehler, prüfe cat expand.sql, korrigiere die vollständige gespeicherte Anweisung und wende sie nur an, wenn die Spalte weiterhin fehlt. Fehler 1060 bei einer wiederholten Erweiterung bedeutet, dass die Spalte bereits existiert; prüfe SHOW COLUMNS, statt sie zu entfernen oder die Datenbank zurückzusetzen. Die Wiederholung einer erfolgreichen Clientbestellung erzeugt einen Fehler wegen doppelter ID: Verwende show für die vorhandene Bestellung, statt eine andere ID zu erfinden. Bewahre die benannten erlaubten Bestellungen und ursprünglichen Daten.

Beobachten, was ein Rollback nicht rückgängig machen kann

In diesem Schritt beobachtest du eine native ALTER-Grenze an einer separaten Demonstrationstabelle und lässt dabei das Bestellsystem intakt.

Fahre in Terminal unter /home/labex/project/pickup-desk fort. ddl_demo ist eine ausdrücklich entbehrliche Lehrtabelle mit einer Zeile, getrennt von allen Bestellungen. Ihre anfängliche Notiz ist original:

./db -e "SELECT * FROM ddl_demo;"

Eine Transaktion fasst Datenänderungen bis COMMIT oder ROLLBACK zusammen. START TRANSACTION beginnt eine; UPDATE ändert die ausgewählte Zeile; ROLLBACK verwirft normalerweise ihre noch nicht bestätigten Datenänderungen. MySQL-DDL (Data Definition Language), einschließlich ALTER TABLE, hat eine implizite Commit-Grenze. ALTER bestätigt vorangehende Arbeit vor dem Ändern der Definition per Commit und wird durch ein späteres Benutzer-ROLLBACK nicht rückgängig gemacht. Die Wiederherstellung atomaren DDL ist nicht dasselbe, wie Benutzer-DDL durch Rollback rückgängig machen zu können.

Die folgende Datei ändert absichtlich nur diese Demonotiz, bevor sie eine Ganzzahlspalte extra ergänzt, die NULL zulässt. Sie fordert dann ROLLBACK an. Überlege vor dem Ausführen, ob Notiz und neue Spalte erhalten bleiben:

cat > ddl-demo.sql <<'SQL'
START TRANSACTION;
UPDATE ddl_demo SET note='committed before ALTER' WHERE id=1;
ALTER TABLE ddl_demo ADD COLUMN extra INT NULL;
ROLLBACK;
SQL
./shop apply ddl-demo.sql
./db -e "SELECT * FROM ddl_demo;"
./db -e "SHOW COLUMNS FROM ddl_demo;"

Die Zeile hat weiterhin die Notiz committed before ALTER, und extra ist NULL. SHOW COLUMNS listet extra weiterhin auf. Das frühere Daten-UPDATE wurde von ALTER per Commit bestätigt, und die neue Definition bleibt ebenfalls bestehen. Dass ROLLBACK erfolgreich zurückkehrte, hat sie nicht rückgängig gemacht. Dies ist tatsächliches Serververhalten, keine erfundene Ausgabedatei.

Lies die tatsächlichen Bestellungen erneut:

./shop show 101
./shop show 201
./shop show 203

Ihre ursprünglichen Kopfwerte, Notizen, Artikel und gespeicherten Abholcodes bleiben erhalten. Führe diese Demonstration niemals an einer Bestellnotiz aus. Eine tatsächliche Migration trennt eine transaktionale Datenergänzung von späterem verschärfendem DDL und plant ihre Wartungs-/Reparaturgrenze entsprechend; jedes ALTER in BEGIN zu setzen, bietet keinen automatischen Rollback.

Die Demodatei ist ein einmaliges Skript aus der angegebenen Ausgangsdefinition. Führst du sie versehentlich zweimal aus, existiert extra bereits. Prüfe die tatsächliche Demodefinition und Zeile; entferne sie nicht, um einen zweiten Lauf neu erscheinen zu lassen. Stelle eine Datei mit Tippfehlern durch Kopieren ihres vollständigen Blocks vor dem ersten erfolgreichen Anwenden wieder her. Diese Einheit endet mit kompatibler Erweiterung und einer ehrlichen DDL-Beobachtung, nicht mit einer Behauptung der Bereitstellung unter durchgehendem Produktivverkehr.

Zusammenfassung

Du hast eine kompatible Erweiterung der Bestelltabelle abgeliefert, tatsächliche Schreibzugriffe des alten und neuen Clients beobachtet und ursprüngliche Bestelldetails bewahrt. Ein isoliertes natives Experiment zeigte, warum ein erfolgreiches ROLLBACK weder ALTER noch dessen zuvor bestätigte Datenänderung rückgängig machen kann. Historische Abholentscheidungen benötigen weiterhin die im nächsten Lab vermittelte freigegebene Zuordnung.