Guide: PHP- & MySQL-innføring: Kapittel 8

Tid for databaser

Vi har til nå dekket svært mye av språket PHP; i dag tar vi tak i MySQL og introduserer begreper som relasjonsdatabase.

Side 1: Introduksjon

MySQL-logoen. Klikk på bildet for å komme til MySQL-hjemmesiden.
MySQL-logoen. Klikk på bildet for å komme til MySQL-hjemmesiden.

For å lage en virkelig dynamisk nettside trenger man en database i bakgrunnen. De aller fleste nettsidene undertegnede har utviklet opp gjennom årene har hatt en database i bakgrunnen. Hardware.no har f.eks. flere store relasjonsdatabaser som lagrer artikler, forumposter og forumbrukere. En database er i dag ganske lett å sette opp, og vil i de fleste tilfeller gi deg en svært dynamisk og rask nettside.

Mange kjenner nok databasebegrepet gjennom produkter som Microsoft Access, men bakgrunnen for databaser er mer kompleks. Databaser begynte ganske enkelt som filer hvor man lagret strukturert data, gjerne oppdelt av spesielle tegn. Såkalte komma-avgrensede filer er et eksempel på denne tankegangen. Etter hvert utviklet man flere ulike modeller for databaser; den hierarkiske modellen er i dag brukt blant annet når man behandler XML-filer. Den mest populære modellen, som også er den modellen vi utelukkende skal konsentrere oss om i denne guiden, er den relasjonelle modellen.

Relasjonsdatabaser lar deg definere relasjoner (sammenhenger) mellom ulike typer data i databasen, og det er mulig å sette sammen data på alle mulige måter. Relasjonsdatabaser består av tabeller. I en tabell finner man en gitt type data, og tabellen er oppdelt i kolonner og rader.

En kolonne kan best beskrives som en overskrift i en tabell, og man angir når man oppretter tabellen hvor mange kolonner den har, og hva som kan lagres i hver enkelt kolonne. Selve dataene i en tabell er radene. Som en hovedregel inneholder en rad en dataverdi for hver kolonne i tabellen.

MySQL er det mest populære relasjonsdatabasesystemet som også er gratis. Det baserer seg på en dialekt av SQL (Structured Query Language, uttales "SQL" eller som engelsk "sequel"), som er et språk som har vært i bruk i de aller fleste databasesystemer siden slutten av 80-tallet. Det betyr at det aller meste av det du lærer deg om MySQL også er overførbart til andre databasesystemer senere, med små endringer.

Side 2: Tilgang til MySQL

Tilgang til MySQL

Vi antar i dag at du innstallerte XAMPP som vi beskrev i del 1 av denne guiden, eller at du kjører et Debian-basert Linux-system. I så fall kan du installere MySQL ved å skrive "apt-get install mysql-server" som root. Om du ønsker å installere alt fra bunnen selv, finner du instruksjoner i MySQL-manualen.

Uansett om du benytter Linux/Unix eller Windows, vil bruken av MySQL være lik med en gang du har funnet de kjørbare filene. På Linux ligger disse i stien, mens med XAMPP på Windows finner du dem i C:\Program files\XAMPP\MySQL\bin. Undertegnede jobber på Linux for øyeblikket, så det blir antatt i eksemplene nedenfor.

For å opprette en oppkobling til MySQL fra kommandolinjen, benytter du deg av programmet mysql (mysql.exe på Windows). Om du ikke har satt noe passord på root-kontoen din, kobler du opp ved å bare skrive "C:\Program files\XAMPP\MySQL\bin\mysql.exe" på Windows, eller bare mysql på Linux. Men dersom du har satt opp et root-passord, må du gjøre følgende;

"C:\Program files\XAMPP\MySQL\bin\mysql.exe" -p

Merk at passordet skrives ikke på kommandolinjen, men du får spørsmål om det når du starter MySQL. Om du også har satt opp en ekstra bruker som du ønsker å benytte, må du bruke -u , og dersom du ønsker å koble til en MySQL-database på en annen datamaskin, bruker du -h .

Om alt går som det skal, ser det gjerne slik ut;

veg@daedalus:~$ mysql -h localhost -u root -p
Enter password:
Welcome to the MySQL monitor.  Commands end with ; or \g.
Your MySQL connection id is 41935 to server version: 
5.0.24a-Debian_9-log

Type 'help;' or '\h' for help. Type '\c' to clear the buffer.

mysql>

Dette kalles MySQL-prompten. Her kan du skrive inn spørringer til MySQL. Om du ønsker å teste, kan du skrive "SHOW DATABASES;" og trykke enter. Du vil da få opp en liste over databasene som finnes på denne MySQL-installasjonen. Alle spørringer i MySQL avsluttes med et semikolon, så du kan spre spørringen din over flere linjer.

Når du nå har fått MySQL opp å kjøre, kan du lage din test-database, som vi kaller "php_guiden". For å opprette denne databasen skriver du bare "CREATE DATABASE php_guiden". Merk at på Linux er database-navn (og tabellnavn) i MySQL versal-sensitive, slik at "php_guiden" er ikke det samme som "PHP_guiden". For å ta i bruk den nye databasen din, skriv "USE php_guiden;", og trykk enter.

Her er en rask oversikt over hvordan dette så ut på mitt system;

mysql> CREATE DATABASE php_guiden;
Query OK, 1 row affected (0.00 sec)

mysql> USE php_guiden;
Database changed
mysql>

På neste side ser vi på datatypene i MySQL, og vi kommer ikke til å bruke databasen vi opprettet her før på siden etterpå. Om du valgte å kalle din database noe annet, noter ned navnet så du husker det.

Side 3: Datatyper

Datatyper

Før man kan lagre data i databasen vår, er vi nødt til å bestemme strukturen på dataene vi vil lagre. Denne strukturen defineres av en tabell-definisjon (noen ganger kalt et tabell-skjema). Som vi har nevnt tidligere, består en tabell av kolonner, og vi må bestemme hvilke data hver kolonne skal inneholde.

Til forskjell fra PHP, er vi i MySQL nødt til å definere hvilken type data som skal lagres i hver kolonne. Det finnes mange datatyper i MySQL, og her er en liste over de viktigste;


Navn Hva den lagrer
Tall
TINYINT Lagrer et heltall mellom -128 og 127. Ved å sette nøkkelordet UNSIGNED foran, endres rekkevidden til 0 til 255.
SMALLINT Lagrer et heltall mellom -32 768 og 32 767. Ved å sette nøkkelordet UNSIGNED foran, endres rekkevidden til 0 til 65 535.
MEDIUMINT Lagrer et heltall mellom -8 388 608 og 8 388 607. Ved å sette nøkkelordet UNSIGNED foran, endres rekkevidden til 0 til 16 777 215.
INT Lagrer heltall, i rekkevidden -2 147 483 648 til 2 147 483 647. Ved å sette nøkkelordet UNSIGNED foran, endres rekkevidden til 0 til 4 294 967 295. Er den vanligste datatypen for å lagre heltall.
BIGINT Lagrer heltall, i rekkevidden -9 223 372 036 854 775 808 til 9 223 372 036 854 775 807. Ved å sette nøkkelordet UNSIGNED foran, endres rekkevidden til 0 til 18 446 744 073 709 551 615. Bør unngås om du ikke trenger å bruke så store tall.
DOUBLE Lagrer flyttal ifølge IEEE-standarden. Tallet er nøyaktig til omtrent 15-desimalplasser.
BOOL En boolsk verdi (TRUE/FALSE). I MySQL er TRUE definert som alle verdier som ikke er 0 eller NULL. Lagres som en TINYINT på disk.
Tidspunkt
DATE Lagrer en dato, på formatet ÅÅÅÅ-MM-DD.
TIME Lagrer et tidspunkt (uten datobiten) på formatet TT:MM:SS.
DATETIME Lagrer en dato og et tidspunkt, på formatet ÅÅÅÅ-MM-DD TT:MM-SS.
TIMESTAMP Lagrer et tidspunkt som antall sekunder fra 1. januar 1970 kl. 00:00:00.
Tekst
CHAR(størrelse) CHAR-datatypen lagrer tekst i et felt med statisk størrelse. Du oppgir størrelsen på feltet i antall tegn (maksimum størrelse er 255). Uansett om du lagrer et tegn, eller så mange tegn som er tillatt, vil det ta størrelse når det lagres på disk (om teksten du lagrer ikke er lang nok, fylles den med NULL-tegn).
VARCHAR(størrelse) Samme som CHAR, men kun den faktiske strengen lagres på disk. Noe tregere enn CHAR.
TEXT Lagrer tekst med en lengde på opptil 216 bytes (64 KiB) med tekst. Bruker kun lengden på teksten som blir lagret på disk.
MEDIUMTEXT Lagrer tekst med en lengde på opptil 224 bytes (16 MiB) med tekst. Bruker kun lengden på teksten som blir lagret på disk.
LONGTEXT(størrelse) Lagrer tekst med en lengde på opptil 232 bytes (4 GiB) med tekst. Bruker kun lengden på teksten som blir lagret på disk.

Om du er interessert i resten av disse datatypene, eller detaljer om de enkelte, finner du dem i MySQL-manualen. På neste side skal vi opprette vår første tabell.

Side 4: Tabeller

Tabeller

Med all vår nyervervede kunnskap om datatyper, er det på tide å opprette vår første tabell. Tabellen vi lager skal brukes til å lagre en liste over personer, med fornavn, etternavn, fødselsdato og e-postadresse. For enkelhets skyld kaller vi tabellen vår person.

For å opprette en tabell, bruker vi en SQL-setning som kalles CREATE TABLE. Uten å gå videre inn på syntaksen, presenterer vi bare spørringen her, og så skal vi gjennomgå den etterpå. Slik ser den ut når vi skriver den direkte inn i MySQL-prompten.


mysql> CREATE TABLE person (
    ->   fornavn VARCHAR(255),
    ->   etternavn VARCHAR(255),
    ->   fodselsdato DATE,
    ->   epost VARCHAR(255)
    -> );
Query OK, 0 rows affected (0.03 sec)

MySQL indikerer nederst at spørringen var OK, og at ingen rader ble påvirket, noe som betyr at vi ikke satte inn noe faktisk data. Syntaksen for CREATE TABLE er ganske enkel; først kommer navnet på tabellen vi skal lage. Deretter følger deklarasjonen av kolonnene, separert av komma. En kolonne begynnes med navnet på kolonnen, etterfulgt av datatypen og en eventuell størrelse (merk at DATE ikke krever noen størrelse).

Om du vil sjekke om tabellen din ble korrekt opprettet, prøv å skrive "DESCRIBE person;". Forhåpentligvis blir resultatet som følger;


mysql> DESCRIBE person;
+-------------+--------------+------+-----+---------+-------+
| Field       | Type         | Null | Key | Default | Extra |
+-------------+--------------+------+-----+---------+-------+
| fornavn     | varchar(255) | YES  |     | NULL    |       |
| etternavn   | varchar(255) | YES  |     | NULL    |       |
| fodselsdato | date         | YES  |     | NULL    |       |
| epost       | varchar(255) | YES  |     | NULL    |       |
+-------------+--------------+------+-----+---------+-------+
4 rows in set (0.00 sec)

Hver rad som vi nå setter inn i person-tabellen, vil nå bestå av et fornavn, et etternavn, en fødselsdato og en e-postadresse. Om du ser i Default-kolonnen i beskrivelsen, ser du også at alle disse verdiene kan settes til NULL (tilsvarer NULL i PHP), og at dette faktisk er standardverdien.

Vi ønsker nå gjerne å sette inn noe data i tabellen vår, slik at vi har noe å teste mot. Vi gjør dette enkelt ved å bruke en INSERT INTO-spørring;


mysql> INSERT INTO person (fornavn, etternavn, fodselsdato, epost)
    -> VALUES ('Vegard', 'Larsen', '1984-02-23', 'vegard AT hardware.no');
Query OK, 1 row affected (0.00 sec)

Du får en indikasjon på at innsettingen var vellykket, og at en rad i tabellen ble påvirket. Du kan sette inn flere rader, slik at vi har noe å teste med;


mysql> INSERT INTO person (fornavn, etternavn, fodselsdato, epost)
    -> VALUES
    -> ('Ola', 'Nordmann', '1974-04-12', 'ola AT eksempel.no'),
    -> ('Kari', 'Nordkvinne', '1932-01-29', 'kari AT eksempel.no'),
    -> ('Per', 'Olsen', '2003-02-01', 'per AT eksempel.no'),
    -> ('Knut', 'Olsen', '1943-10-12', 'knut AT eksempel.no');
Query OK, 4 rows affected (0.00 sec)
Records: 4  Duplicates: 0  Warnings: 0

Her ser du at vi har satt inn flere verdier i en spørring, og at vi får noe mer informasjon ut fra MySQL i dette tilfellet. Nå har vi nok data til å begynne å undersøke innholdet i tabellen.

Side 5: Uthenting av data

Uthenting av data

Vi har til nå lagd en tabell, og satt inn noe data i den. Du har kanskje satt inn noe ekstra data i forhold til hva jeg gjorde, og det går bra; men du kan få forskjellige resultater enn vi gjør i våre eksempler her.

Siden tabellen vår er så liten (den har bare 5 rader), kan det være praktisk å hente ut alle dataene som er her; og det gjøres svært enkelt med en SELECT-spørring;


mysql> SELECT * FROM person;
+---------+------------+-------------+-----------------------+
| fornavn | etternavn  | fodselsdato | epost                 |
+---------+------------+-------------+-----------------------+
| Vegard  | Larsen     | 1984-02-23  | vegard AT hardware.no |
| Ola     | Nordmann   | 1974-04-12  | ola AT eksempel.no    |
| Kari    | Nordkvinne | 1932-01-29  | kari AT eksempel.no   |
| Per     | Olsen      | 2003-02-01  | per AT eksempel.no    |
| Knut    | Olsen      | 1943-10-12  | knut AT eksempel.no   |
+---------+------------+-------------+-----------------------+
5 rows in set (0.00 sec)

Her ser du at vi har fått ut dataene i den rekkefølgen vi la den inn (det er ikke nødvendigvis tilfellet). Alt vi har lagt inn er der fremdeles. * indikerer at vi vil ha data fra alle kolonner i tabellen. Det er gjerne ikke så interessant, sett at vi ville ha listen alfabetisert etter etternavn;


mysql> SELECT * FROM person ORDER BY etternavn;
+---------+------------+-------------+-----------------------+
| fornavn | etternavn  | fodselsdato | epost                 |
+---------+------------+-------------+-----------------------+
| Vegard  | Larsen     | 1984-02-23  | vegard AT hardware.no |
| Kari    | Nordkvinne | 1932-01-29  | kari AT eksempel.no   |
| Ola     | Nordmann   | 1974-04-12  | ola AT eksempel.no    |
| Per     | Olsen      | 2003-02-01  | per AT eksempel.no    |
| Knut    | Olsen      | 1943-10-12  | knut AT eksempel.no   |
+---------+------------+-------------+-----------------------+
5 rows in set (0.00 sec)

Om du studerer listen nøye, ser du gjerne at Per kommer før Knut, selv om det alfabetisk ikke er korrekt. En ny spørring fikser på det;


mysql> SELECT * FROM person ORDER BY etternavn, fornavn;
+---------+------------+-------------+-----------------------+
| fornavn | etternavn  | fodselsdato | epost                 |
+---------+------------+-------------+-----------------------+
| Vegard  | Larsen     | 1984-02-23  | vegard AT hardware.no |
| Kari    | Nordkvinne | 1932-01-29  | kari AT eksempel.no   |
| Ola     | Nordmann   | 1974-04-12  | ola AT eksempel.no    |
| Knut    | Olsen      | 1943-10-12  | knut AT eksempel.no   |
| Per     | Olsen      | 2003-02-01  | per AT eksempel.no    |
+---------+------------+-------------+-----------------------+
5 rows in set (0.00 sec)

Du kan selvsagt bruke ORDER BY til å sortere på de andre kolonnene også; f.eks. kan du rangere etter alder slik som dette;


mysql> SELECT * FROM person ORDER BY fodselsdato DESC;
+---------+------------+-------------+-----------------------+
| fornavn | etternavn  | fodselsdato | epost                 |
+---------+------------+-------------+-----------------------+
| Per     | Olsen      | 2003-02-01  | per AT eksempel.no    |
| Vegard  | Larsen     | 1984-02-23  | vegard AT hardware.no |
| Ola     | Nordmann   | 1974-04-12  | ola AT eksempel.no    |
| Knut    | Olsen      | 1943-10-12  | knut AT eksempel.no   |
| Kari    | Nordkvinne | 1932-01-29  | kari AT eksempel.no   |
+---------+------------+-------------+-----------------------+
5 rows in set (0.00 sec)

Her har vi lagt til nøkkelordet DESC (en forkortelse for descending) for å indikere at vi ønsker den største datoen først, dvs. den yngste personen.

Kanskje er vi bare interessert i å hente ut en gitt kolonne fra tabellen vår, la oss si at vi skal lage en e-postliste og vi bare trenger e-postadressene;


mysql> SELECT epost FROM person;
+-----------------------+
| epost                 |
+-----------------------+
| vegard AT hardware.no |
| ola AT eksempel.no    |
| kari AT eksempel.no   |
| per AT eksempel.no    |
| knut AT eksempel.no   |
+-----------------------+
5 rows in set (0.00 sec)

Som du ser kan vi bruke MySQL til å hente ut nøyaktig den informasjonen vi trenger fra en tabell, ved å benytte enkle spørringer.

Side 6: Mer uthenting

Mer uthenting

Til nå har vi bare sortert utdataene når vi henter data fra MySQL, men det er ofte mye nyttigere å bare hente ut den nøyaktige informasjonen vi trenger. Til dette bruker vi en såkalt WHERE-klausul, som lar deg velge bort rader ved hjelp av samme logikk som vi benytter i PHP.

Likhet

Sett at vi lurer på om det er noen som har bursdag i dag i databasen vår (det er det ikke, så vi får et tomt resultat);



mysql> SELECT * FROM person WHERE fodselsdato = CURDATE();
Empty set (0.00 sec)

Selv om resultatet er tomt, illustrerer det to viktige ting; først og fremst at det finnes mange innebygde funksjoner i MySQL. Her bruker vi funksjonen CURDATE() til å hente ut dagens dato. For det andre benytter vi oss av en WHERE-klausul som sier at vi kun ser etter personer som har en gitt fødselsdato. Du kan også se at i MySQL bruker vi et enkelt likhetstegn for å sjekke om noe er likt, mens vi i PHP må benytte to likhetstegn.

Vi kan også se etter personer som har et gitt etternavn;


mysql> SELECT * FROM person WHERE etternavn = 'Olsen';
+---------+-----------+-------------+---------------------+
| fornavn | etternavn | fodselsdato | epost               |
+---------+-----------+-------------+---------------------+
| Per     | Olsen     | 2003-02-01  | per AT eksempel.no  |
| Knut    | Olsen     | 1943-10-12  | knut AT eksempel.no |
+---------+-----------+-------------+---------------------+
2 rows in set (0.00 sec)

Vi bruker også her likhetstegnet for å sjekke at innholdet i en kolonne er en gitt verdi, men denne gangen gjør vi det på en string-kolonne. Kanskje vi ønsker å finne alle som har et etternavn som begynner på bokstaven N? Da må vi bruke en annen sammenligning.

Strenglikhet


mysql> SELECT * FROM person WHERE etternavn LIKE 'N%';
+---------+------------+-------------+---------------------+
| fornavn | etternavn  | fodselsdato | epost               |
+---------+------------+-------------+---------------------+
| Ola     | Nordmann   | 1974-04-12  | ola AT eksempel.no  |
| Kari    | Nordkvinne | 1932-01-29  | kari AT eksempel.no |
+---------+------------+-------------+---------------------+
2 rows in set (0.00 sec)

Her bruker vi sammenligningen LIKE, og prosenttegnet angir da et såkalt wildcard for å spesifisere at her kan det komme en rekke på flere bokstaver. Du kan sette inn prosenttegn flere plasser i søkestrengen, og du kan også plassere det fremst. For å finne alle som har e-postadresse hos Hardware.no kan du bruke denne spørringen;


mysql> SELECT * FROM person WHERE epost LIKE '% AT hardware.no';
+---------+-----------+-------------+-----------------------+
| fornavn | etternavn | fodselsdato | epost                 |
+---------+-----------+-------------+-----------------------+
| Vegard  | Larsen    | 1984-02-23  | vegard AT hardware.no |
+---------+-----------+-------------+-----------------------+
1 row in set (0.00 sec)

Du kan også søke etter ikke-treff; om du vil ha personer som ikke jobber for Hardware.no, kan du bruke denne spørringen;


mysql> SELECT * FROM person WHERE epost NOT LIKE '% AT hardware.no';
+---------+------------+-------------+---------------------+
| fornavn | etternavn  | fodselsdato | epost               |
+---------+------------+-------------+---------------------+
| Ola     | Nordmann   | 1974-04-12  | ola AT eksempel.no  |
| Kari    | Nordkvinne | 1932-01-29  | kari AT eksempel.no |
| Per     | Olsen      | 2003-02-01  | per AT eksempel.no  |
| Knut    | Olsen      | 1943-10-12  | knut AT eksempel.no |
+---------+------------+-------------+---------------------+
4 rows in set (0.00 sec)

Den eneste forskjellen fra spørringen over er ordet NOT før LIKE, og meningen er selvsagt. Om du skal gjøre det samme når du bruker likhetstegnet til å sammenligne, må du bytte ut likhetstegnet med !=, som er det samme som i PHP.

Større enn/mindre enn

Hva om du vil ha alle som født i eller etter 1977 (som gjør at de er 30 år eller yngre i år);



mysql> SELECT * FROM person WHERE fodselsdato >= '1977-01-01';
+---------+-----------+-------------+-----------------------+
| fornavn | etternavn | fodselsdato | epost                 |
+---------+-----------+-------------+-----------------------+
| Vegard  | Larsen    | 1984-02-23  | vegard AT hardware.no |
| Per     | Olsen     | 2003-02-01  | per AT eksempel.no    |
+---------+-----------+-------------+-----------------------+
2 rows in set (0.00 sec)

Du kan her bruke en rekke av de samme sammenligningsoperatorene som i PHP, og de fungerer også på strenger. Om du vil ha alle som kommer etter Nordkvinne i telefonkatalogen, kan du bruke følgende spørring;


mysql> SELECT * FROM person WHERE etternavn > 'Nordkvinne';
+---------+-----------+-------------+---------------------+
| fornavn | etternavn | fodselsdato | epost               |
+---------+-----------+-------------+---------------------+
| Ola     | Nordmann  | 1974-04-12  | ola AT eksempel.no  |
| Per     | Olsen     | 2003-02-01  | per AT eksempel.no  |
| Knut    | Olsen     | 1943-10-12  | knut AT eksempel.no |
+---------+-----------+-------------+---------------------+
3 rows in set (0.00 sec)

Selv om vi har utelukket alle som har et etternavn som er alfatbetisk mindre enn Nordkvinne, ser du at resultatet likevel ikke er sortert korrekt på fornavn og etternavn. Dette må vi spesifisere om vi ønsker, og det gjør vil på følgende måte;


mysql> SELECT * FROM person
    -> WHERE etternavn > 'Nordkvinne'
    -> ORDER BY etternavn, fornavn;
+---------+-----------+-------------+---------------------+
| fornavn | etternavn | fodselsdato | epost               |
+---------+-----------+-------------+---------------------+
| Ola     | Nordmann  | 1974-04-12  | ola AT eksempel.no  |
| Knut    | Olsen     | 1943-10-12  | knut AT eksempel.no |
| Per     | Olsen     | 2003-02-01  | per AT eksempel.no  |
+---------+-----------+-------------+---------------------+
3 rows in set (0.00 sec)

Det er viktig å bite seg merke i at WHERE alltid kommer før ORDER BY, men ellers er dette bare en sammenslåing av det du har lært til nå.

Side 7: Hva med NULL?

Hva med NULL

Som vi nevnte tidligere, kan alle feltene i tabellen vår ha en NULL-verdi, som tilsvarer noe av det samme som det gjør i PHP. Vi bruker hovedsaklig verdien NULL i MySQL når det er en kolonne som ikke gjelder for denne raden.

For eksempel, om vi skal legge inn musikkartisten Madonna i tabellen vår, ville vi gjort det med en NULL-verdi på etternavn og e-postadresse. Dette kan vi gjøre på en av to måter, enten ved å eksplisitt sette inn NULL i de relevante feltene når vi setter inn, eller lage en INSERT spørring der de relevante kolonnene ikke er nevnt. Her er begge metodene;


mysql> INSERT INTO person (fornavn, fodselsdato)
    -> VALUES ('Madonna', '1958-08-16');
Query OK, 1 row affected (0.00 sec)

mysql> INSERT INTO person (fornavn, etternavn, fodselsdato, epost)
    -> VALUES ('Madonna', NULL, '1958-08-16', NULL);
Query OK, 1 row affected (0.00 sec)

Om du nå henter ut alle med fornavn Madonna fra databasen, vil du se følgende;


mysql> SELECT * FROM person WHERE fornavn = 'Madonna';
+---------+-----------+-------------+-------+
| fornavn | etternavn | fodselsdato | epost |
+---------+-----------+-------------+-------+
| Madonna | NULL      | 1958-08-16  | NULL  |
+---------+-----------+-------------+-------+
1 row in set (0.00 sec)

Om du skal lete etter personer som ikke har etternavn i databasen din, vil du måtte bruke en spesiell sjekk for å finne dem, fordi du kan ikke benytte WHERE etternavn = NULL i spørringen siden NULL er en spesialverdi.


mysql> SELECT * FROM person WHERE etternavn = NULL;
Empty set (0.00 sec)

mysql> SELECT * FROM person WHERE etternavn IS NULL;
+---------+-----------+-------------+-------+
| fornavn | etternavn | fodselsdato | epost |
+---------+-----------+-------------+-------+
| Madonna | NULL      | 1958-08-16  | NULL  |
+---------+-----------+-------------+-------+
1 row in set (0.00 sec)

Som du ser krever NULL litt spesiell behandling om du skal hente ut data basert på slike verdier.

Side 8: Oppdatering

Oppdatering

Sett at du en dag oppdager at Madonna faktisk også har et etternavn, og du har lyst til å oppdatere dette i databasen din. Da kan du enten slette den originale raden og sette inn en ny, men dette kan føre til trøbbel med relasjoner til andre tabeller (som du ennå ikke har lært særlig mye om, og så har du ikke lært å slette noe enda).

For å oppdatere rader i tabellen er du nødt til å bruke en UPDATE-spørring. Den krever også en WHERE-klausul, ellers så endrer den alle rader i tabellen din til de nye verdiene. Du bruker den på følgende måte for å sette Madonnas korrekte fornavn og etternavn;


mysql> UPDATE person SET
    ->   fornavn = 'Madonna Louise',
    ->   etternavn = 'Ciccone Ritchie'
    -> WHERE fornavn = 'Madonna'
    -> LIMIT 1;
Query OK, 1 row affected (0.01 sec)
Rows matched: 1  Changed: 1  Warnings: 0

Selve UPDATE-biten av denne spørringen er ganske lett å forstå; vi oppdaterer både fornavnet og etternavnet med nye verdier. Dette gjør vi bare dersom fornavnet allerede er satt til 'Madonna'. Den siste linjen har du ikke sett før, og betyr rett og slett at MySQL bare får lov til å endre en enkelt rad. Du kan endre tallet dersom det er nødvendig. Du kan også benytte LIMIT sammen med SELECT-spørringer, og dette er veldig trygt å eksperimentere med. Strengt tatt er ikke LIMIT påkrevd i spørringen over, siden det faktisk kun finnes en rad i tabellen hvor fornavnet er eksakt lik 'Madonna', men den er kjekk å bruke som et sikkerhetsnett i tilfelle det var flere rader som hadde det samme fornavnet.

Det kan ofte være lurt å sjekke på forhånd om de radene UPDATE faktisk vil endre er de samme som du ønsker å oppdatere. Det gjør du enklest ved å benytte nøyaktig samme WHERE-klausul i en SELECT-spørring.

Du kan nå forsikre deg om at du har oppdatert den korrekte raden som du ønsket;


mysql> SELECT * FROM person WHERE fornavn LIKE 'M%';
+----------------+-----------------+-------------+-------+
| fornavn        | etternavn       | fodselsdato | epost |
+----------------+-----------------+-------------+-------+
| Madonna Louise | Ciccone Ritchie | 1958-08-16  | NULL  |
+----------------+-----------------+-------------+-------+
1 row in set (0.00 sec)

Side 9: Sletting

Sletting

Hva om du har informasjon i tabellen din som du ønsker å slette? La oss si at du ikke lenger liker Madonna, og ikke ønsker å ha henne i din kontaktliste; da er du nødt til å benytte deg av en DELETE-spørring.

Før vi begynner, DELETE er akkurat like utsatt for å glemme WHERE-klausulen som UPDATE er. Derfor bør du alltid være veldig forsiktig når du forsøker å slette ting fra tabellene dine, og huske å ha med en tilstrekkelig WHERE-klausul, og gjerne også en LIMIT-bit.


mysql> SELECT * FROM person WHERE fornavn LIKE 'Madonna%';
+----------------+-----------------+-------------+-------+
| fornavn        | etternavn       | fodselsdato | epost |
+----------------+-----------------+-------------+-------+
| Madonna Louise | Ciccone Ritchie | 1958-08-16  | NULL  |
+----------------+-----------------+-------------+-------+
1 row in set (0.00 sec)

mysql> DELETE FROM person WHERE fornavn LIKE 'Madonna%' LIMIT 1;
Query OK, 1 row affected (0.00 sec)

Vi sjekket først hvor mange rader det fantes med et fornavn som begynner med Madonna, og deretter kjører vi en DELETE-spørring med samme WHERE-klausul og en begrensning på antallet. Selve syntaksen til DELETE er ganske enkel, og trenger ikke videre forklaring.

Side 10: Oppsummering

Oppsummering

I dag har du lært det aller mest grunnleggende om relasjonsdatabaser, og MySQL spesielt. Du har lært at en database består av en eller flere tabeller, og at en tabell er oppbygd av kolonner og rader.

Vi har vist deg hvordan du kobler opp mot en MySQL-database. Etterpå fortalte vi om de ulike datatypene en MySQL-tabell kan bestå av, før vi viste deg hvordan du kan lage dine egne tabeller, og hvordan du kan sette inn data i dem. Du har senere sett hvordan vi kan benytte MySQL til å finne spesifikk informasjon i databasen på en enkel måte, gjennom språket SQL. Her har du lært sortering og utvelgelse.

Vi har vist deg hvordan du kan oppdatere data som du har lagt inn i databasen, og til slutt hvordan du kan slette disse dataene. Vi har også hatt en rask gjennomgang av den spesielle NULL-verdien.

Neste gang

Neste gang vil vi fortsette å lære deg om god bruk av databaser, og hvordan du bør sette opp tabellene dine for å få effektiv utnyttelse av en database. Vi vil vise deg hvordan du kan sette flere tabeller i sammenheng, og dermed lage mer avanserte spørringer.