| af Martin Elsman og Niels Hallenberg | sidst rettet 15. februar, 2002 |
Øvelsen er opdelt i fire opgaver:
Det kan betale sig, at være omhyggelig med de tre første opgaver.
create table SQL-kommandoer.For hver plade i databasen skal der som et minimum være tilknyttet en pladetitel, et kunstnernavn, et udgivelsesår og en samling sangtitler.
Det er nødvendigt at oprette mindst to tabeller; den ene tabel kan
således indeholde pladetitel, kunstnernavn, udgivelsesår og et tal til
at identificere en plade (f.eks. plade_id integer primary
key); den anden tabel kan så indeholde tilknytninger af
sangtitler til hver plade_id. Det anbefales, at man
anvender et tal til at indentificere en sang (f.eks. sang_id
integer primary key).
Til brug for oprettelse af nye plader i databasen skal du oprette
to sekvenser (Oracle: sequence), f.eks.:
create sequence plade_id_sequence start with 10; create sequence sang_id_sequence start with 10;
En datamodel, uden detaljer, kan f.eks. se således ud:
Du skal huske at overveje
varchar(...) og integer
not null.
unique
references.
drop table skal din rækkefølge være
korrekt. Antag f.eks., at du anvender to tabeller tab1 og
tab2, hvor tab2 refererer til
tab1, dvs. databasen checker at der til alle rækker i
tab2 findes refererede rækker i tab1. Så skal
du slette tab2 før du sletter tab1,
idet rækkerne i tab2 jo henviser til rækker i
tab1.
/web/login/www/oevelse10/pladekartotek.sql på hug.it.edu sammen med sql-kode for
indsættelse af to pladeemner i tabellerne. Endelig skal du starte
SQL*Plus på hug.it.edu ved brug af ssh og udføre sql-kommandoerne:
SQL> @/web/login/www/oevelse10/pladekartotek.sql ... SQL> commit;SQL*Plus kommandoen
commit sikrer at dine
tabel-indsættelser bliver synlige for andre SQL*Plus vinduer og for
din web-server. Det er vigtigt, at du husker commit.
insert into pk_plade (plade_id, titel, kunstner, aar) values (plade_id_sequence.nextval, 'Abbey Road', 'Beatles', '1969');
hvor jeg har kaldt tabellen med plader for pk_plade.
insert into pk_sang (plade_id, sang_id, titel) values (38, sang_id_sequence.nextval, 'Here comes the sun'); -- 38 er plade_id for Beatles' Abbey Road
hvor alle sange er nummereret med sang_id. Jeg har kaldt
tabellen med sange for pk_sang.
Som ovenfor skal du opskrive eksempler på SQL-kommandoer for følgende transaktioner:
plade_id
(select). Du skal som minimum vise pladenavn, kunstner og
sangtitler.
select). Du skal som minimum vise pladenavn, kunstner og
sangtitler.
Gem SQL-kommandoerne i en fil
/web/login/www/oevelse10/transaktioner.sql på hug.it.edu.
Indgangssiden til pladekartoteket er vist som en kasse øverst i diagrammet, som kan implementeres som en HTML-fil. De resterende kasser (tilstande) i diagrammet skal implementeres som Tcl-filer, da disse kasser repræsenterer dynamiske sider (d.v.s., hvad brugeren ser i sin browser afhænger af indholdet i databasen og af eventuelle form-argumenter). Du kan også vælge at lade siden "Vis alle plader" være indgangssiden.
Det er din opgave at gøre tegningen ovenfor færdig. På hver at de tre resterende pile skal du skrive navn på det Tcl-program som kaldes samt angive hvilke form-variable der overføres.
For at bestemme hvilke form-variable der skal overføres, så anbefaler
jeg at du kun overfører dem der er absolut nødvendige - altså hold
antallet af form-variable så lavt som muligt. Eksempelvis, hvis du
skal vise sange til en plade, så er plade_id nok idet
alle oplysninger om sange og plade kan hentes fra databasen. Der er
ingen grund til også at overføre pladetitel, selvom at du gerne vil
vise den sammen med sangene - pladetitlen findes jo i databasen.
I den vejledende løsning indgår 6 filer:
pk_vis_plader.tcl, som viser alle plader i databasen
pk_add_plade.tcl, som tilføjer en plade til
kartoteket.
pk_slet_plade.tcl, som sletter en plade. Hvis der er
sange tilknyttet pladen, så slettes sangene før pladen slettes.
pk_vis_sange.tcl, som viser alle sange knyttet til
en bestemt plade. Denne fil anvendes af to pile i diagrammet ovenfor.
pk_add_sang.tcl, som tilføjer en sang til en bestemt
plade.
pk_slet_sang.tcl, som sletter en enkelt sang knyttet
til en bestemt plade.
Det anbefales, at du laver en tegning svarende til den ovenfor. På alle pile skal der være annoteret en Tcl-fil samt de form-variable som overføres til Tcl-filen.
Til denne opgave skal du aflevere
/web/login/www/oevelse10/pladekartotek.html på hug.it.edu, som er indgangssiden til
pladekartoteket. HTML-filen skal indeholde et link til Tcl-filen for
visning af alle pladeemner i databasen.
/web/login/www/oevelse10/struktur.txt, eller som
en tegning svarende til den ovenfor, hvor der på alle pile er noteret
både Tcl-program og de form-variable som overføres. Hvis du vælger at
aflevere en tegning, så kan du evt. scanne en tegning skrevet i
hånden, og overføre filen til hug.it.edu
som /web/login/www/oevelse10/struktur.gif.
Start med at konstruere de dynamiske sider for kasserne i diagrammet. Indsæt også links i disse sider til Tcl-filerne for database-transaktionerne.
For database-transaktionerne kan du med fordel benytte Tcl-kommandoen
ns_returnredirect urlDenne kommando returnerer en besked til browseren om at vise siden
url. Her er kode til implementation af
database-transaktionen for indsaettelse af en sang for en given plade
i databasen:
proc return_page {plade_id} {
ns_returnredirect "pk_vis_sange.tcl?plade_id=$plade_id"
}
# set the form variables `QQsangtitel' and `plade_id'
set_the_usual_form_variables 0
# Test plade_id og sangtitel!
if { ![info exists plade_id] ||
![regexp {^[0-9]*$} $plade_id]} {
ns_return 200 text/html "Panik, der er ikke angivet en plade_id."
return
}
if { ![info exists sangtitel] ||
![string length [string trim $sangtitel]]} {
ns_return 200 text/html "Panik, der er ikke angivet en sangtitel."
return
}
set insert_sql "insert into sangtitler (plade_id, sang_id, sangtitel)
values ($plade_id, sang_id_seq.nextval, '$QQsangtitel')"
set db [ns_db gethandle]
ns_db dml $db $insert_sql
# instead of returning a page to the user with `thank you'
# information, we ask the browser to show the - now updated -
# song page; notice that the dynamic page `pk_sange_vis.tcl' takes
# a form variable `plade_id' as argument.
return_page $plade_id
Bemærk at det ikke kræves af brugeren at der indtastes et password for at slette og oprette data i pladekartoteket.
Gem filerne til opgaverne ovenfor på hug.it.edu i kataloget
/web/login/www/oevelse10/.