Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 Inhaltsverzeichnis Inhaltsverzeichnis ................................................................................................... 1 Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das WS08 ... 2 Das Wichtigste zuerst - zum Ausschneiden und Dabeihaben ................................. 2 Konventionen .......................................................................................................... 3 Dateistruktur............................................................................................................ 3 Dateinamen............................................................................................................. 3 Excel-Datei in ASCII-Dateien umwandeln ............................................................... 3 Eigenschaften der Word-Dokumentation ................................................................ 3 Wie können Sie Auszüge aus Notepad++ dokumentieren ...................................... 4 Environment am CADCAM-Labor ........................................................................... 4 XAMPP ................................................................................................................... 4 Umlaute, ß und besondere Zeichen in anderen Sprachen (Character set) ............. 5 HTML................................................................................................................... 5 SQL ..................................................................................................................... 6 MySQL .................................................................................................................... 6 Starten von MySQL in der Eingabeaufforderung ................................................. 6 Ladedatei............................................................................................................. 7 Beispiel ................................................................................................................ 7 Ausführen von SQL-Dateien ................................................................................ 7 Drop, Create und Use einer Datenbank .............................................................. 7 Löschen einer Tabelle und Kreieren mit Schlüssel und Constraints .................... 8 Laden von Tabellen ............................................................................................. 8 Umleiten der Ausgaben (tee) ............................................................................... 8 Benutzerdefinierte Variablen ............................................................................... 8 Nützliches ............................................................................................................ 8 Fortgeschrittenes ................................................................................................. 9 Join ...................................................................................................................... 9 Guter und erwünschter SQL-Programmierstil ...................................................... 9 HTML und XHTML ................................................................................................ 10 HTML --> XHTML .............................................................................................. 10 Bilder transparent machen ................................................................................ 11 Guter und erwünschter HTML-Programmierstil ................................................. 11 Beispiel für XHTML 1.0 Frameset = index.html ................................................. 11 Beispiel für XHTML 1.0 Strict = quellen.html ..................................................... 12 CSS....................................................................................................................... 12 Guter und erwünschter CSS-Programmierstil ................................................... 12 Beispiel für CSS = dortmund.css ....................................................................... 13 PHP....................................................................................................................... 14 Allgemeines ....................................................................................................... 14 SQL unter PHP .................................................................................................. 14 MySQL-Befehle.............................................................................................. 15 Guter und erwünschter PHP-Programmierstil ................................................... 15 IF.................................................................................................................... 15 1 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 SWITCH......................................................................................................... 16 WHILE ........................................................................................................... 16 DO-WHILE ..................................................................................................... 16 FOR ............................................................................................................... 16 FOREACH ..................................................................................................... 16 PHP-Fehler finden ............................................................................................. 16 Beispiel für eine PHP-Seite = datenbankverbindung.php .................................. 17 Beispiel für eine PHP-Seite mit einem Scrollbar = abfrage_01.php................... 17 Beispiel für eine PHP-Seite mit GoogleMap = abfrage_02.php ......................... 19 Beispiel für eine PHP-Seite mit zwei Scrollbars = abfrage_05.php ................... 21 JavaScript ............................................................................................................. 23 Google Maps mit JavaScript ................................................................................. 23 Google-Koordinaten .......................................................................................... 24 Beispiel 1 = GoogleMap.html............................................................................. 24 Beispiel 2 = GoogleMap2.php ........................................................................... 25 Beispiel 3 ........................................................................................................... 27 Fehlersuche ....................................................................................................... 28 Projektanalyse Hamburg ....................................................................................... 29 Unterlagen ......................................................................................................... 29 Tabellen............................................................................................................. 29 Abfragen ............................................................................................................ 30 Fazit................................................................................................................... 30 Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das WS08 Das Wichtigste zuerst - zum Ausschneiden und Dabeihaben Projektanalyse zuerst In Word nur mnemotechnisch sinnvolle Formatvorlagen Dateistruktur des Projektes einhalten Programmierstile für SQL, HTML, PHP, CSS und JS beachten In allen Codierungen Kommentare und Bezeichner in Englisch In allen Codierungen keine Tabs verwenden Eine einzige SQL-Ladedatei SQL-Abfragen zunächst ohne HTML-Oberfläche testen Fehlermeldungen in C:\Programme\xampp\apache\logs\error.log müssen behoben werden. Ein- und Ausgaben in fehlerfreiem Deutsch mit ß und Umlauten und korrekte Buchstaben in anderen Sprachen, z.B. ç! Transparente Logos, wo erforderlich. Fehlerfreie HTML- und CSS-Dokumente, dazu HTML- und CSS-Seiten validieren lassen. Ebenso von PHP erzeugte HTML-Seiten. Kompatibel zu UNIX, daher gleiche Dinge immer gleich nennen, nicht einmal "Linie", ein andermal "linie". 2 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 Universelle Einsetzbarkeit anstreben. Projektspezifische Teile auslagern in Dateien, die eingelesen werden. Präsentation und Beantwortung einer Abfrage in einer einzigen php-Seite. notepad++ nutzen: Dieser Editor unterstützt Ihre Arbeit, dadurch daß Sie erstens viele Dateien gleichzeitig laden und durchsuchen können und zweitens eine sehr gute Hervorhebung der Syntax für SQL, HTML, PHP, CSS und JS haben. Konventionen <irgendetwas> steht für etwas, das konkret zu ersetzen ist. Dateistruktur Alle Dateien liegen in dem Ordner <familienName>. Dieser Ordner enthält folgende Unterordner: Ordner csv der csv-Dateien. Der Ordner enthält für jede Arbeitsmappe eine Datei. Ordner docu mit der Dokumentation <familienName> in Word und allen eingebundenen Graphiken. Ordner grafics der Bilder und Karten. Ordner lst der Dateien mit allen durch die SQL-Befehle erzeugten Ausgaben. Die Dateien haben die Dateierweiterung lst. Ordner <projektStadt> mit den MySQL-Datenbank-Dateien. Ordner sql der Dateien mit allen Befehlen der DDL und DML der Projektbearbeitung durch den Vorgänger (zum Beispiel query01_alt.sql) und durch Sie selbst query01.sql. Die Dateien haben die Dateierweiterung sql. Der Ordner enthält auch die Ladedatei <projektStadt>.sql. Ordner xls mit einer xls-Datei mit den verschiedenen, benannten Arbeitsmappen. Ordner www mit allen HTML- und PHP-Dateien. Dateinamen Es ist ausgesprochen unklug, wenn Sie bei Dateibezeichnern und Variablen Sonderzeichen wie "ü" und "ß" verwenden. Excel-Datei in ASCII-Dateien umwandeln Die ASCII-Dateien entstehen aus der xls-Datei durch Datei/Speichern unter…/Text(Tapstopp-getrennt)(*.txt) oder durch Datei/Speichern unter…/ CSV(Trennzeichen-getrennt)(*.csv) Eigenschaften der Word-Dokumentation Die Word-Datei darf nur selbst definierte Formatvorlagen enthalten. Es sollen zumindest diese enthalten sein: Überschrift1 bis 3, Standard (man kann die vorhergehenden vier nicht entfernen, aber ändern), Codierung, hervorgehobenFett, Eingabelegende, Ausgabelegende, Abbildungslegende. Verwenden Sie Flattersatz mit automatischer Silbentrennung. Es dürfen keine leeren Absätze und keine zwei Leerzeichen hintereinander vorkommen (Danach kann man übrigens suchen!). Das Dokument soll automatisch erstellte Inhalts-, Eingabe-, Ausgabe- und Abbildungsverzeichnisse enthalten. Die Eingabe-, Ausgabe- und Abbildungsdateien sollen automatisch eingebunden werden. Bitte weisen Sie nach, welche Programme Sie genutzt haben Die Lesbarkeit und der Informationsgehalt Ihres Textes sind wichtig. 3 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 Mit Ihrer Internet-Anwendung treten Sie an die Öffentlichkeit. Daher die Rechtschreibung so sorgfältig wie bei Ihrer Abschlußarbeit prüfen. Orthographie- und Interpunktionsfehler sind im Internet besonders ärgerlich und (dis)qualifizieren sofort den Verfasser. Wie können Sie Auszüge aus Notepad++ dokumentieren In Notepad++ haben Sie eine html-, css-, php- oder sql-Datei geladen. Die Syntax ist jeweils farblich hervorgehoben. Nun möchten Sie bestimmte Zeilen in eine PowerPoint-Präsentation oder eine WordDatei einfügen; insbesondere mit den farblichen Hervorhebungen, möglichst auch mit den Zeilennummern, aber nicht als Screenshot, da er immer nur schlecht zu lesen ist und Sie ihn nicht punktuell ändern können. Das können Sie so schaffen: In Notepad++ ergänzen Sie in den Zeilen zusätzliche(!) Zeilennummern. Dann exportieren Sie den gewünschten Zeilenbereich in den Zwischenspeicher im rtfFormat. Aus dem Zwischenspeicher können Sie dann ganz normal nach Word oder Powerpoint importieren. Die zusätzlichen Zeilennummern erhalten Sie mit TextFX/TextFX Tools/Insert Line Numbers. In den Zwischenspeicher exportieren Sie mit Erweiterungen/NppExport/Copy RTF to clipboard. Environment am CADCAM-Labor Die Rechner im CADCAM-labor sind so eingerichtet, daß man auf einer virtuellen Maschine seinen eigenen Server einrichten kann. Damit kann man das Zusammenspiel von Server und Browser durch serverseitige und browserseitige Programmierung kennen lernen. Voraussetzung ist jedoch, daß man sich jeweils am gleichen Rechner anmeldet. Die virtuelle Maschine startet man mit Start/Programme/VMware/VMware Player. Im Fenster "Öffnen" gibt man ein: d\vmware\winxppro.vmx. Damit laufen auf dem Rechner jetzt die reale und die virtuelle Maschine. Auf der virtuellen Maschine arbeitet man immer als Administrator. Beim ersten Mal muß man das Passwort des Administrators setzen. Ordner und Dateien kann man durch "drag and drop" leicht zwischen den Maschinen hin- und herbewegen. Auf das CD-Laufwerk und den USB-Stick kann man von der virtuellen Maschine direkt zugreifen. Dem <ctrl><alt><entf> auf der realen Maschine entspricht <ctrl><alt><einfg> auf der virtuellen Maschine. Die virtuelle Maschine soll immer ordentlich beendet werden. XAMPP Apache, MySQL, PHP und Perl sind auf einer XAMPP-Datei vorinstalliert. Die Vorinstallation steht auf der realen Maschine auf o:/tmp. Man zieht die Vorinstallation auf die virtuelle Maschine und führt sie aus. Gibt man jetzt in einem Browser als URL http://localhost/projekt ein, wird eine Datei c:/xampp/htdocs/projekt/index.html (bzw. index.php oder index.htm) gesucht und dargestellt. MySQL-Datenbanken sind auf c:/xampp/mysql/data abgelegt. 4 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 Umlaute, ß und besondere Zeichen in anderen Sprachen (Character set) Das Problem bei der Verwendung besonderer Zeichen wie Ä, Ö, Ü. ä, ö, ü, ß ist, daß Sie dafür Sorge tragen müssen, daß diese Zeichen auch auf englischen oder ungarischen Rechnern unter UNIX oder Windows korrekt erscheinen. Sie können die Zeichen verwenden, wenn Sie in HTML- und sql-Dateien die unten aufgeführten Einzelheiten beachten. Es ist zu unterscheiden, ob die Zeichen im HTML-Code oder in der sql-Ladedatei stehen. HTML Im Header steht die Zeile: <meta http-equiv="Content-Type" content="text/html; charset=latin-1"> Im Body werden die Zeichen gemäß der Spalte ISO 8859-1 eingetragen. Darstellung ISO 8859-1 Ä &Auml; Ö &Ouml; Ü &Uuml; ä &auml; ö &uuml; ü &ouml; ß &szlig; â &acirc; é &eacute; è &egrave; ê &ecirc; É &Eacute; Î &Icirc; ô &ocirc; œ &oelig; ç &ccedil; © &copy; € &euro; & &amp; „ “ ‚ ‘ &bdquo; &ldquo; &sbquo; &lsquo; 5 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 SQL Sie bearbeiten die sql-Ladedatei mit Notepad++. Tabellennamen und Spaltennamen sind in Englisch. Dabei entstehen keine Probleme. Bei den Inhalten der Spalten wie "Bülowstraße" setzen Sie die Zeichen, wie Sie das in Word gewohnt sind. Der Anfang der Ladedatei sieht dann so aus: SET @@SESSION.CHARACTER_SET_RESULTS='cp850'; DROP DATABASE IF EXISTS test; SHOW WARNINGS; CREATE DATABASE IF NOT EXISTS test; SHOW WARNINGS; USE test; SHOW WARNINGS; DROP TABLE IF EXISTS tabelle; SHOW WARNINGS; CREATE TABLE IF NOT EXISTS tabelle ( id INTEGER, name VARCHAR(30) ); SHOW WARNINGS; Wenn Sie die Ladedatei jetzt abspeichern und in einem Eingabefenster mit mysql einlesen, wundern Sie sich, daß trotzdem die Zeichen nicht korrekt dargestellt werden. Jetzt machen Sie folgendes in Notepad++: Im Menü "Format" steht "UTF-8 ohne BOM". Sie wählen "Konvertiere zu ANSI". Abermals in "Format" jetzt "Konvertiere zu MAC", dann in "Format" wieder "Konvertiere zu UNIX". Das Ergebnis speichern und fertig!! Ich habe keinen einfacheren Weg gefunden, ohne UNIX zu verwenden. Wer kennt einen? Das Problem mit Umlauten â, á, à und dergleichen habe ich bearbeitet. Wie diese Zeichen in HTML aussehen sollten ist klar, wie sie aber in eine Datenbank hineinkommen und wieder gelesen werden können, ist nicht klar gewesen. Erst in UltraEdit habe ich gesehen, woran das liegt. Gute Dateien sehen binär so aus: 73 65 74 20 40 40 73 65 73 73 69 6F 6E 2E 63 68 ; set @@session.ch Schlechte so: FF FE 73 00 65 00 74 00 20 00 40 00 40 00 73 00 ; ÿþs.e.t. .@[email protected]. Hinweis von Malte Ahrens: HTML- und SQL-Dateien in Notepad++ bearbeiten und speichern: neue Datei anlegen - Haken bei "Format" - "Kodiere als UTF-8 (ohne BOM)" setzen; [Option bei "Kodiere als ANSI" ist bereits beim Anlegen der Datei aktiviert] Header der HTML-Dateien: <meta http-equiv="content-type" content="text/html; charset=UTF-8"/> Umlaute in der HTML-Datei brauchen nicht mehr mittels "benannter Zeichen" kodiert werden - es kann also auf &Auml; verzichtet werden. SQL-Datenbank anlegen: CREATE DATABASE IF NOT EXISTS `mainz` DEFAULT CHARACTER SET utf8 COLLATE utf8_general_ci; MySQL Starten von MySQL in der Eingabeaufforderung Wenn MySQL korrekt installiert wurde, kann man es in der Eingabeaufforderung starten mit: mysql -u user –ppasswort 6 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 Achtung! Zwischen -u und dem Benutzernamen ist ein Leerzeichen, zwischen -p und dem Paßwort dagegen nicht Ladedatei Das Einrichten der Datenbank, das Kreieren und Füllen der Tabellen erfolgt am besten mit der Ladedatei <projektStadt>.sql. Mit der Ladedatei kann man die gesamte Datenbank mit einer Anweisung löschen und erneuern (s. u.). Die Ladedatei <projektStadt>.sql soll daher gleich zu Beginn der Projektarbeiten erstellt werden. Und zwar deshalb, weil in der Regel Umbenennungen der Tabellennamen und Spaltennamen notwendig sind. Damit erstrecken sich diese Änderungen nicht auf mehrere Dateien, sondern erfolgen in einer einzigen Datei. Falls im Laufe des Projekts weitere Änderungen erfolgen müssen, werden sie jeweils in der Ladedatei vorgenommen. Beispiel SET @@SESSION.CHARACTER_SET_RESULTS='cp850'; DROP DATABASE IF EXISTS dortmund; SHOW WARNINGS; CREATE DATABASE IF NOT EXISTS dortmund; SHOW WARNINGS; USE dortmund; SHOW WARNINGS; DROP TABLE IF EXISTS karten; SHOW WARNINGS; CREATE TABLE IF NOT EXISTS karten ( id INT2 UNSIGNED NOT NULL, name VARCHAR(30) BINARY, xlinks INT4 DEFAULT NULL, yoben INT4 DEFAULT NULL, xrechts INT4 DEFAULT NULL, yunten INT4 DEFAULT NULL, typ VARCHAR(20) BINARY, PRIMARY KEY (id) ); SHOW WARNINGS; INSERT INTO karten (id, name, xlinks, yoben, xrechts, yunten, typ) VALUES (81, 'detail3.png', 392000, 5706910, 395200, 5704268, 'Detail'), (80, 'detail2.png', 390342, 5712552, 392496, 5709138, 'Detail'), (79, 'detail1.png', 392000, 5709080, 394856, 5707046, 'Detail'), (78, 'uebersicht.png', 0, 0, 0, 0, 'Übersicht'); SHOW WARNINGS; weitere Tabellen mit create und insert Beachten Sie bitte den Befehl show warnings; Er gibt Hinweise auf Unstimmigkeiten, untersucht aber nur den vorangegangenen Befehl. Daher muß für die Einfügungen eine spezielle, nur bei MySQL erlaubte Form gewählt werden! Ausführen von SQL-Dateien Die Dateien mit den SQL-Befehlen kann man so in MySQL ausführen: source C:/<familienName>/sql/query01.sql; Drop, Create und Use einer Datenbank Drop, Create und Use einer Datenbank werden so vorgenommen: DROP DATABASE IF EXISTS <projektStadt>; CREATE DATABASE IF NOT EXISTS <projektStadt>; USE <projektStadt>; 7 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 Löschen einer Tabelle und Kreieren mit Schlüssel und Constraints DROP TABLE IF EXISTS linien; CREATE TABLE linien ( id SMALLINT UNSIGNED NOT NULL AUTO_INCREMENT, farbe CHAR(15) NOT NULL DEFAULT ’ ’, typ ENUM(’1’, ’2’, ’3’), PRIMARY KEY (id), FOREIGN KEY (typ) REFERENCES typ (typ) ON DELETE NO ACTION ON UPDATE NO ACTION ); Laden von Tabellen Die Angaben der Dateipfade sind entweder relativ zum bin-Ordner des MySQLServers oder absolut. LOAD DATA INFILE ’../temp/linien.txt’ INTO TABLE linien; LOAD DATA LOCAL INFILE ’H:\\linien.csv’ INTO TABLE linien FIELDS TERMINATED BY ’;’ ENCLOSED BY ’ ’ LINES TERMINATED BY ’\n’; LOAD DATA INFILE "C:/Programme/MySQL/MySQL Server 5.0/data/gaststaetten.csv" INTO TABLE gaststaetten FIELDS TERMINATED BY ';' /* auch ’\t’ möglich*/ LINES TERMINATED BY '\r\n'; Wenn nach dem Laden eine Tabelle eine unerklärliche, verdorbene Spaltenstruktur hat, ist der Ladeprozeß mit falschen Parametern durchgeführt worden. Umleiten der Ausgaben (tee) Die folgende Umleitung der Ausgabe verwendet man, wenn die Ausgabe weiterverarbeitet werden soll. Für unsere Dokumentationszwecke ist sie nicht geeignet. SELECT * FROM linien INTO OUTFILE ’linien.lst’ FIELD TERMINATED BY ’|’; Wenn man die eigentlichen SQL-Befehle mit den beiden folgenden Zeilen klammert, erhält man eine für unsere Zwecke geeignete Dokumentationsdatei: \T <Pfad>\<datei>.lst \t Benutzerdefinierte Variablen Mit benutzerdefinierten Variablen kann man Ausdrücke bilden. Man kann aber keine Namen von Tabellen oder Spalten dabei nutzen. SET @var_name = expr [, @var_name = expr] ... SELECT @min_price:=MIN(price),@max_price:=MAX(price) FROM shop; SELECT * FROM shop WHERE price=@min_price OR price=@max_price; Soweit ich sehe, gibt es keine Möglichkeit, alle vereinbarten benutzerdefinierten Variablen aufzulisten. Nützliches Zum Zeigen der MySQL-Kommandos (nicht Standard-SQL): HELP; Zum Zeigen der Umgebungsvariablen: SHOW VARIABLES; Umgebungsvariablen setzt man mit: set @@session.<variable>=<value>; set @@global.<variable>=<value>; Zum Zeigen der Datenbanken: 8 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 SHOW DATABASES; Zum Zeigen der Tabellen: SHOW TABLES; Zum Zeigen der Spalten einer Tabelle: SHOW COLUMNS FROM <tabelle>; Die gleiche Wirkung hat: DESCRIBE <tabelle>; Fortgeschrittenes Benutzerdefinierte Variablen: set @haltestelle=’ETTlinger TOR’; An der Stelle einer FROM-Tabelle kann ein SELECT stehen: SELECT AVG(x_lo) FROM (SELECT x_lo FROM karten) k; Gruppenfunktion GROUP_CONCAT: SELECT h_id, COUNT(*), GROUP_CONCAT(DISTINCT l_id ORDER BY l_id SEPARATOR ’, ’) AS ’Linien’ FROM hl GROUP BY h_id; Reguläre Ausdrücke: SELECT * FROM haltestellen WHERE hochwert REGEXP ’^540[0-9]+’; Case: SELECT h_id, CASE WHEN 1 THEN ’Park + Ride’ WHEN 2 THEN ’Bike + Ride’ ELSE ’ ’ END AS ’Ausstattung’ FROM hl; Limit: SELECT * FROM haltestellen LIMIT 5, 10; In Oracle entspricht das in etwa: ROWNUM < 10 Join 1) tblref1, tblref2 oder tblref1 [CROSS] JOIN tblref2 oder tblref1 STRAIGHT_JOIN tblref2 2) tblref1 INNER JOIN tblref2 joincond 3) tblref1 LEFT [OUTER] JOIN tblref2 joincond oder tblref1 RIGHT [OUTER] JOIN tblref2 joincond 4) tblref1 NATURAL [LEFT [OUTER]] JOIN tblref2 oder tblref1 NATURAL [RIGHT [OUTER]] JOIN tblref2 Wenn sich tblref1 und tblref2 auf die gleiche Tabelle beziehen, sprecht man von einem Auto- oder Self-Join. Bei 1) kann auch eine Bedingung in der Form WHERE tblref1. joinfield1 op tblref2. joinfield2 stehen. Bei 2) und 3) hat joincond die Form ON tblref1. joinfield1 op tblref2. joinfield2, auch USING(joinfield). Bei 4) muß es in tblref1 und tblref2 übereinstimmende Spaltennamen joinfield geben. Ist der Vergleichsoperator op das Gleichheitszeichen, spricht man von einem Equi-Join, sonst von einem Not-Equi-Join. Guter und erwünschter SQL-Programmierstil Im Programmcode sollen keine Tabulatoren verwendet werden, da sie von unterschiedlichen Editoren unterschiedlich umgesetzt werden. SQL-spezifische Bezeichner in upper-case, aber benutzerdefinierte in lower-case; also z.B. SELECT, ROUND, aber linien, name. Die Bezeichner für Entitäten-Tabellen stehen im Plural; also haltestellen. Die Bezeichner für Relationen-Tabellen werden mit einem Verb gebildet; also h_liegtauf_l (in diesem Fall verkürzt zu h_l). 9 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 Die Primärschlüssel der Tabellen heißen immer id, Namen heißen immer name; es sei denn Sie brauchen z.B. vorname und nachname. Die Aliase für Tabellen sollen möglichst nur aus einem Buchstaben bestehen und den Tabellennamen aufnehmen; also linien AS l, haltestellen AS h. Wählen Sie einprägsame Bezeichner. Sie sollen nicht zu kurz sein, aber auch nicht zu lang. x_koordinate ist zu lang, hier ist x sogar ausreichend. Im Sinne der Internationalisierung sollten Sie Bezeichner und Kommentare in Englisch wählen. In den SELECT-Anweisungen dürfen keine unbenannten Konstanten enthalten sein: verboten sind also zum Beispiel WHERE name='Ettlinger Tor' und auch WHERE entfernung < 500. Wenn Sie eine Anweisung auf mehrere Zeilen verteilen, dann ist das Ende einer Klausel eine geeignete Trennstelle. Vor dem Komma kein Leerzeichen, danach ein Leerzeichen. Vor und nach <, >, = ein Leerzeichen. Vor und nach dem Punkt kein Leerzeichen. HTML und XHTML Die für Ihre Internet-Anwendung erforderlichen Dateien liegen im Ordner www. Legen Sie im Ordner xampp/htdocs einen Ordner <projektStadt> an. In diesem Ordner liegen Kopien der Dateien aus dem Ordner www. Insbesondere liegt dort Ihre Startdatei mit dem Namen index.html oder index.php; in jedem Fall index. Dann können Sie Ihr Projekt mit http://localhost/<projektStadt> durch den Server auf Ihrem Browser präsentiert bekommen. Umlaute, ß und copyright werden so realisiert: &Auml; &uuml; &szlig; &copy; Bilder als Icons sollen transparent auf dem Untergrund stehen und keinen weißen Rand haben. Wie man das erreicht, siehe unten. Seiten, die unterhalb von index.html liegen, werden mit einem relativen Pfad angegeben. Also nicht: http://localhost/<projektStadt>/query01.php sondern: ./query01.php Das setzt voraus, daß index.html und query01.php im gleichen Ordner liegen. Wenn query01.php im Unterordner "queries" liegt, dann geht es so: ./queries/query01.php Beachten Sie einmal "./", das andere Mal "../". Ihre Lösungen möchte ich später auf meiner Homepage ins Netz stellen, siehe www.hans-f-kern.de/PDB.shtml. HTML --> XHTML Für die Einbindung von Google-Maps in Internetseiten wird der Einsatz von XHTML empfohlen. Wenn man in HTML korrekt gearbeitet hat und sich nicht zu sehr auf die Gutmütigkeit der Browser verlassen hat, ist die Umstellung auf XHTML nicht sehr aufwendig. Hier folgen die wichtigsten Punkte. <br> wird zu <br /> Jedes Tag hat ein End-Tag oder eine entsprechende Gestalt. <P CLASS=menue> wird zu <p class="menue"> Alle Elemente und Attribute werden klein geschrieben. Die Attributwerte werden in " oder ' eingeschlossen. NORESIZE wird zu noresize="noresize" Alle Elemente und Attribute werden klein geschrieben. Jedes Attribut hat einen Attributwert. 10 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 Bilder transparent machen Bei den Logos möchte man in der Regel Transparenz erreichen. Das kann man mit Photoshop machen, aber auch so: Öffnen Sie http://www.gifworks.com/ Klicken Sie "How do I get started?" Click here to begin. Man kann das Bild hochladen, transparent machen und wieder herunterladen. Guter und erwünschter HTML-Programmierstil Keine absoluten Pfade verwenden, sondern immer relativ zum Ordner von index.html. Ihre HTML-Dokumente sollen möglichst auf allen Betriebssystemen und allen Browsern richtig dargestellt werden. bei Pfad- und Dateinamen unterscheiden Windows und Internet-Explorer nicht zwischen Groß- und Kleinschreibung, UNIX wohl. Nicht an einer Stelle grau.jpg, an anderer Grau.JPG verwenden! Im Programmcode sollen keine Tabulatoren verwendet werden, da sie von unterschiedlichen Editoren unterschiedlich umgesetzt werden. Wählen Sie einprägsame Bezeichner. Sie sollen nicht zu kurz sein, aber auch nicht zu lang. Im Sinne der Internationalisierung sollten Sie Bezeichner und Kommentare in Englisch wählen. In reinen HTML-Dateien sollen Klammerungen durch Einrückungen sichtbar gemacht werden. Bei umfangreichen Dokumenten führt das zu einer zu tiefen Staffelung. Dann kann man die Einrückungen vereinfachen, wie das unten bereits für <title> und <a> gezeigt ist. Ob Ihr HTML-Dokument fehlerfrei ist, können Sie unter validator.w3.org überprüfen. Beispiel für XHTML 1.0 Frameset = index.html <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Frameset//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-frameset.dtd"> <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en"> <head> <title>Das Stra&szlig;enbahnnetz der Stadt Dortmund</title> <link rel="stylesheet" media="all" type="text/css" href="dortmund.css" /> <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1" /> </head> <frameset cols="30%,*"> <frameset rows="10%,*"> <frame src="obenlinks.html" name="obenlinks" scrolling="no" noresize="noresize" frameborder="0" /> <frame src="verweise.html" name="Verweise" scrolling="yes" noresize="noresize" frameborder="0" /> </frameset> <frameset rows="17%,*"> <frame src="oben.html" name="oben" scrolling="no" noresize="noresize" frameborder="0" /> <frame src="startseite.html" name="Daten" scrolling="yes" noresize="noresize" frameborder="0" /> </frameset> <noframes> <body> <p> 11 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 <a href="verweise.html">Verweise</a> <a href="startseite.html">Daten</a> </p> </body> </noframes> </frameset> </html> Beispiel für XHTML 1.0 Strict = quellen.html <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"> <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en"> <head> <title>ER-Modell</title> <link rel="stylesheet" media="all" type="text/css" href="dortmund.css" /> <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1" /> </head> <body> <p class="menue">Verwendete Literatur:</p> <p>Wolfgang D. Misgeld: ORACLE f&uuml;r Profis, Hanser, 1991</p> <p>Stefan Mintert (Hg.): XHTML, CSS &amp; Co, Addison-Wesley, 2003</p> <p>Self-HTML <a href="http://de.selfhtml.org/index.htm"> http://de.selfhtml.org/index.htm</a></p> <p>Self-PHP <a href="http://www.selfphp.net/selfphp/"> http://www.selfphp.net/selfphp/</a></p> </body> </html> CSS Guter und erwünschter CSS-Programmierstil Die typographische Gestaltung einer Seite soll nicht "fest verdrahtet" sein, sondern mit Hilfe von CSS realisiert werden. Damit kann man die meisten Attribute in Marken, die die Typographie beeinflussen, vermeiden. Statt zum Beispiel auf der HTML-Seite im Element body das Attribut bgcolor und die mißbilligten Attribute text und background zu verwenden, <body bgcolor="#FF9900" text="#FF0000" background="bild.gif"> soll in der CSS-Datei stehen: body { background-color : #FF9900; background-image :url(bild.gif); color : #FF0000; } Statt zum Beispiel auf der HTML-Seite die Element font und b zu verwenden, <p><font face="Arial, sans-serif" size="3" color="#660000"> <b>Gegenstand</b> </font></p> soll in der CSS-Datei stehen: p { font-family : Arial, sans-serif; font-size : 10pt; color : #660000; font-weight : bold; } 12 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 Darstellungsorientierte Marken wie <b>, <br>, <i>, <u> sollen ganz vermieden werden. Auch die Verwendung von &nbsp; ist nicht erwünscht. Es sollen keine absoluten Positionsangaben verwendet werden. style="position:absolute; right:26px; top:15px" Die Bildschirme der Benutzer haben jeweils unterschiedliche Auflösungen und es kann dann alles durcheinander geraten. Es ist gerade ein Konstruktionsprinzip des Web, daß auch bei Verkleinerung des Darstellungsfensters alles lesbar bleibt. Probieren Sie es aus! Was passiert, wenn Sie den Bildschirm verkleinern? Das meiste verrutscht in sinnvoller Weise. Den Hinweis "Optimiert für Browser xyz mit Auflösung nnn" empfinde ich als eine Ausrede. Im Programmcode sollen keine Tabulatoren verwendet werden, da sie von unterschiedlichen Editoren unterschiedlich umgesetzt werden. Wählen Sie einprägsame Bezeichner. Sie sollen nicht zu kurz sein, aber auch nicht zu lang. Im Sinne der Internationalisierung sollten Sie Bezeichner und Kommentare in Englisch wählen. Ob Ihr CSS-Dokument fehlerfrei ist, können Sie unter jigsaw.w3.org/css-validator überprüfen. Beispiel für CSS = dortmund.css /* Es sollten hier saemtliche Tags aufgefuehrt sein, die verwendet werden. Zum Beispiel: a, body, div, em, h1, h2, h3, h4, h5, img, li, ol, p, table, td, th, tr, ul, */ a:link { color : #006699; text-decoration : none; } a:visited { color : #006699; text-decoration : none; } a:hover { color : #006699; text-decoration : none; background-color : #ffbbaa; } a:active { color : #006699; text-decoration : none; background-color : #ffbbaa; } p { font-size : 10pt; color : #000000; font-family : Tahoma; } p.menue { font-size : 10pt; font-weight : bold; color : #006699; font-family : Tahoma; } p.untermenue { 13 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 font-size : 9pt; font-weight : bold; color : #ff866a; font-family : Tahoma; } input, textarea { font-size : 10pt; color : #000000; font-family : Tahoma; } span.dick { font-size : 10pt; color : #000000; font-family : Tahoma; font-weight : bold; } PHP Allgemeines Die Abfragen sollen immer als Frage formuliert werden und zwar so, daß aus dem Text eindeutig hervorgeht, was der Benutzer auszuwählen hat? Zum Beispiel: Welche auszuwählende Haltestelle hat einen tiefen Einstieg? Der Benutzer muß also eine Haltestelle auswählen! Welche Haltestellen haben einen tiefen Einstieg? Der Benutzer muß hier nichts auswählen! Keine absoluten Pfade verwenden, sondern immer relativ zum Ordner von index.html. Ihre PHP-Dokumente sollen möglichst auf allen Betriebssystemen und allen Browsern richtig dargestellt werden. bei Pfad- und Dateinamen unterscheiden Windows und Internet-Explorer nicht zwischen Groß- und Kleinschreibung, UNIX wohl. Nicht an einer Stelle grau.jpg, an anderer Grau.JPG verwenden! Für die Behandlung einer Abfrage soll nur eine (!) PHP-Datei eingesetzt werden. Im Programmcode sollen keine Tabulatoren verwendet werden, da sie von unterschiedlichen Editoren unterschiedlich umgesetzt werden. Der PHP-Quelltext soll mit <?php eingeleitet werden, <? kann zu Fehlern führen. Wählen Sie einprägsame Bezeichner. Sie sollen nicht zu kurz sein, aber auch nicht zu lang. x_koordinate ist zu lang, hier ist x sogar ausreichend. Im Sinne der Internationalisierung sollten Sie Bezeichner und Kommentare in Englisch wählen. Pro Zeile nur eine Anweisung. Vor dem Komma kein Leerzeichen, danach ein Leerzeichen. Vor und nach <, >, =, -> kein Leerzeichen. SQL unter PHP Da Ihre Projekt-Applikation von beliebigen Nutzern verwendet wird, können Sie diesen Benutzern natürlich keine Veränderungen in Ihrer Datenbank gestatten. Sie müssen also alle die Datenbank ändernden Befehle vermeiden. Das folgende SQLBeispiel zeigt, wie man ein CREATE umgehen kann. CREATE TABLE dist AS SELECT MAX(entf) maxim FROM h_l GROUP BY l_id; SELECT SUM(maxim) FROM dist; wird zu SELECT SUM(dist.maxim) FROM (SELECT MAX(entf) maxim FROM h_l GROUP BY l_id) dist; 14 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 Hier sieht man, daß an der Stelle einer FROM-Tabelle auch ein SELECT stehen kann. MySQL-Befehle Das Ergebnis einer SELECT-Anweisung ist eine Tabelle mit Zeilen und Spalten, wobei die Spalten Namen haben. Mit mysql_query erhält man einen Handle - Pointer - auf das Ergebnis einer SELECT-Anweisung. $query = "SELECT name, x, y FROM haltestellen"; $result = mysql_query($query) OR die("Mist! ". mysql_error()); Die Anzahl der Zeilen erhält man mit: $rows = mysql_num_rows($result1); Die Anzahl der Spalten erhält man mit: $cols = mysql_num_fields($result1); An den Wert in der 5. Zeile und 3. Spalte kommt man mit: $y=mysql_result($result, 5, 3); Wenn man alle Zeilen und Spalten eines SELECT verarbeiten möchte, kann man das so machen: $query = "SELECT name, x, y FROM haltestellen"; $result = mysql_query($query) OR die("Mist! ". mysql_error()); $rows = mysql_num_rows($result); $cols = mysql_num_fields($result); for($r=0; $r< $rows; $r++) { for($c=0; $c<$cols; $c++) { $name = mysql_result($result, $r, 0); $x = mysql_result($result, $r, 1); $y = mysql_result($result, $r, 2); verarbeite $name, $x, $y } } Eine ganze Zeile erhält man mit: $row = mysql_fetch_object($result); Die Verarbeitung aller Zeilen und Spalten kann man so eleganter erledigen: $query = "SELECT name, x, y FROM haltestellen"; $result = mysql_query($query) OR die("Mist! ". mysql_error()); while ($row = mysql_fetch_object($result)) { $name = $row->name; $x = $row->x; $y = $row->y; verarbeite $name, $x, $y } Wenn ein Handle nicht mehr gebraucht wird, soll man es freigeben mit: mysql_free_result($result); Guter und erwünschter PHP-Programmierstil Zur besseren Lesbarkeit sollen immer { und } eingesetzt werden, auch in den Fällen, in denen es nicht zwingend ist. Dort, wo im folgenden anweisung steht, können auch mehrere Anweisungen stehen. Einrückungen nur dort, wo es in der Programmstruktur eine Etage tiefer geht; also wie unten gezeigt IF if (ausdruck) { anweisung; } elseif (ausdruck) { anweisung; 15 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 } else { anweisung; } SWITCH switch (ausdruck) { case ausdruck: anweisung; break; case ausdruck: anweisung; break; default: anweisung; break; } WHILE while (ausdruck) { anweisung; } DO-WHILE do { anweisung; } while (ausdruck); FOR for (start_ausdruck; cond_ausdruck; iter_ausdruck) { anweisung; } FOREACH foreach [array_ausdruck as $wert) { anweisung; } PHP-Fehler finden Wie kann man Fehler in PHP besser lokalisieren und dann beheben? Dazu gibt es die PHP-Funktion error_log. Die Funktion heißt zwar error_log, mit ihr läßt sich aber insbesondere der Ablauf des PHP-Programms verfolgen. Die Anwendung zeige ich Ihnen in einer kleinen PHP-Datei. <?php # Es gibt eine vordefinierte Funktion error_log(text,action) zur Dokumentation von # Fehlern. # Damit kann man erstens verfolgen, durch welche Codeteile das Programm gelaufen # ist, und zweitens kann man sich den Inhalt von Variablen ausgeben lassen. # Der erste Parameter enthält einen frei gewählten Text. # Der zweite Parameter kann diese Werte haben: # 0 Ausgabe der Fehlermeldung auf die Standardfehlerdatei; # in der Regel xampp/apache/logs/error.log # 1 Fehler wird per E-Mail verschickt; in der Regel abgeschaltet. # 3 Fehler wird auf eine private Datei ausgegeben; # im Beispiel error-log-file.log 16 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 error_log("Meine erste Fehlermeldung\n",0); error_log("Meine zweite Fehlermeldung\n",1,"[email protected]"); error_log("Meine dritte Fehlermeldung\n",3,"error-log-file.log"); $a = "hugo"; $b = "hugo "; if ($a == $b) { error_log("Die Variable \$a hat den Wert ***$a***.". " Dieser stimmt mit dem Wert der Variablen \$b überein.\n",3, "error-log-file.log"); } else { error_log("Die Variable \$a hat den Wert ***$a***.". " Dieser stimmt nicht mit dem Wert der Variablen \$b überein.\n",3, "error-log-file.log"); } # Sie haben natürlich in diesem einfachen Beispiel sofort gesehen, daß das Programm # durch den else-Block läuft; denn $a enthält 4 Zeichen, $b dagegen 5. # Der Wert einer der kritischen Variablen wird ebenfalls gezeigt. $buchstaben = range('a', 'z'); error_log("Die Variable \$buchstaben hat den Wert *$buchstaben*. \n",3, "error-log-file.log"); error_log("Die Variable \$buchstaben[1] hat den Wert *$buchstaben[1]*. \n",3, "error-log-file.log"); ?> Beispiel für eine PHP-Seite = datenbankverbindung.php <?php /* Datenbankserver - In der Regel die IP */ $db_server = "localhost"; /* Datenbankname */ $db_name = "dortmund"; /* Datenbankuser */ $db_user = "root"; /* Datenbankpasswort */ $db_passwort = "geheim"; /* Erstellt Connect zu Datenbank her */ $db = @MYSQL_CONNECT($db_server,$db_user,$db_passwort); mysql_select_db($db_name,$db) OR die("Mist! ".mysql_error()); ?> Beispiel für eine PHP-Seite mit einem Scrollbar = abfrage_01.php <?php require_once('datenbankverbindung.php'); echo "<head>"; echo "<title>Abfrage_01</title>"; echo "<link rel='stylesheet' media='all' type='text/css' href='dortmund.css'>"; echo "<meta http-equiv='Content-Type' content='text/html; charset=iso-8859-1'>"; 17 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 echo "</head>"; echo "<body>"; echo "<p class='menue'>Es werden die Sehensw&uuml;rdigkeiten angezeigt, die"; echo "man zu einem gew&auml;hlten maximalen Eintrittspreis besuchen kann.</p>"; echo "<p>Der Eintrittspreis f&uuml;r Kinder ist stets &euro; 0.</p>"; if (array_key_exists('erwachsene_preis',$_GET)) Eingaben { Begin Holen der Form- $erwachsene_preis = $_GET['erwachsene_preis']; } else { $erwachsene_preis = ""; } Ende Holen der Form-Eingaben if ($erwachsene_preis != "") { Beginn Form-Auswertung echo "<p class='untermenue'>Sie haben als maximalen Eintrittspreis &euro;"; echo " $erwachsene_preis ausgew&auml;hlt.</p>"; $query = "SELECT name FROM sehenswuerdigkeiten WHERE erw_preis<= $erwachsene_preis ORDER BY name"; $result = mysql_query($query) OR die("Mist! ". mysql_error()); } else { echo "<p class='untermenue'>Bitte w&auml;hlen Sie den maximalen "; echo "Eintrittspreis pro Erwachsenem!</p>"; } Ende Form-Auswertung echo "<form action='' method='submit'>"; Beginn echo "<select name='erwachsene_preis' size='1'>"; Form-Aufbau $query = "SELECT DISTINCT erw_preis FROM sehenswuerdigkeiten ORDER BY erw_preis"; $result1 = mysql_query($query); if ($result1) { $rows = mysql_num_rows($result1); $cols = mysql_num_fields($result1); for($r=0; $r< $rows; $r++) { for($c=0; $c<$cols; $c++) { echo mysql_result($result1, $r, $c), ", "; echo "<option name='erwachsene_preis'>"; echo mysql_result($result1, $r, $c); echo "</option>"; } } } else { echo "Fehler"; } echo "</select>"; echo "<input type='submit' value='OK'>"; echo "</form>"; Ende Form-Aufbau if ($erwachsene_preis != "") { Beginn abermals Form-Auswertung if ($result) { echo "<p><span class='dick'>Die m&ouml;glichen Sehensw&uuml;rdigkeiten:"; echo "</span><p>"; $rows=mysql_num_rows($result); 18 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 $cols=mysql_num_fields($result); for ($r=0; $r<$rows; $r++){ for ($c=0; $c<$cols; $c++){ echo mysql_result($result, $r, $c); echo "<br>"; } } echo "</p>"; } } Ende abermals echo "</body>"; ?> Form-Auswertung Beispiel für eine PHP-Seite mit GoogleMap = abfrage_02.php <?php require_once('datenbankverbindung.php'); echo "<head>"; echo "<title>Abfrage_02</title>"; echo "<link rel='stylesheet' media='all' type='text/css' href='dortmund.css'>"; echo "<meta http-equiv='Content-Type' content='text/html; charset=iso-8859-1'>"; echo "<script type='text/javascript'>"; echo "function FensterOeffnen (Adresse) { "; echo "MeinFenster = window.open(Adresse, 'Detailkarte', 'scrollbars=yes'); "; echo "MeinFenster.focus();"; echo "}"; echo "</script>"; echo ' <script src="http://maps.google.com/maps?file=api&amp;v=2&amp;key=ABQIAAAAzosMcEBJXrsEQFGBQ AWclRQgU1QyBe_kcGDWdfFXsq08_1MSqxREpHLDVDDm5p9ub3kwCQeYethC1w" type="text/javascript"> </script> '; echo "</head>"; echo '<body border="0" onload="load()" onunload="GUnload()">'; echo "<p class='menue'>Es wird zu einer gew&auml;hlten Sehensw&uuml;rdigkeit eine GoogleMap angezeigt.</p>"; echo "<p>&nbsp;</p>"; if (array_key_exists('poi',$_GET)) { $poi = $_GET['poi']; } else { $poi = ""; } if ($poi != "") { echo "<p class='untermenue'>Sie haben die Sehensw&uuml;rdigkeit ".$poi." ausgew&auml;hlt.</p>"; $sql = "SELECT x, y, name FROM sehenswuerdigkeiten WHERE name ='".$poi."'"; $result = mysql_query($sql) OR die("Mist! ". mysql_error()); } else { echo "<p class='untermenue'>Bitte w&auml;hlen Sie eine Sehensw&uuml;rdigkeit!</p>"; } 19 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 echo "<form action='' method='submit'>"; echo "<select name='poi' size='1'>"; $sql = "SELECT DISTINCT name FROM sehenswuerdigkeiten ORDER BY name "; $result1 = mysql_query($sql) OR die("Mist! ". mysql_error()); if ($result1) { $rows = mysql_num_rows($result1); $cols = mysql_num_fields($result1); for($r=0; $r< $rows; $r++) { for($c=0; $c<$cols; $c++) { echo mysql_result($result1, $r, $c), ", "; echo "<option name='poi'>"; echo mysql_result($result1, $r, $c); echo "</option>"; } } } else { echo "Fehler result1"; } echo "</select>"; echo "<input type=submit value='OK'>"; echo "</form>"; if ($result) { $rows = mysql_num_rows($result); $cols = mysql_num_fields($result); for($r=0; $r< $rows; $r++) { $xobj[$r] = mysql_result($result, $r, 0); $yobj[$r] = mysql_result($result, $r, 1); $nobj[$r] = mysql_result($result, $r, 2); } } /* Berechnung von GK nach WGS84*/ include './gaussk.php'; for($r=0; $r< $rows; $r++) { $xin=$xobj[$r]+3000015; $yin=$yobj[$r]+1845; $wgs84array = CalcStart($xin, $yin); $xobj[$r] = $wgs84array[0]; $yobj[$r] = $wgs84array[1]; } $zoom = "15"; /* Freigeben des Resultsets, d.h. Leeren des Speichers der Variable $result */ mysql_free_result($result); echo '<script type="text/javascript">'; echo ' function load() { function createListener (marker, text) { GEvent.addListener(marker, "click", function() { marker.openInfoWindowHtml(text); } 20 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 ); } if (GBrowserIsCompatible()) { var map = new GMap2(document.getElementById("map")); map.addControl(new GLargeMapControl()); map.addControl(new GMapTypeControl()); map.addControl(new GScaleControl()); map.addControl(new GOverviewMapControl()); '; echo ' map.setCenter(new GLatLng('.$xobj[0].', '.$yobj[0].'), '.$zoom.', G_SATELLITE_MAP); var point = new Array(); var text = new Array(); var marker = new Array(); '; for ($r=0; $r<$rows; $r++) { echo ' point['.$r.'] = new GLatLng('.$xobj[$r].','.$yobj[$r].'); text['.$r.'] = "'.$nobj[$r].'"; '; } echo ' var marker = new Array(); for (i=0; i< point.length; i++) { marker[i] = new GMarker(point[i]); map.addOverlay(marker[i]); createListener (marker[i], text[i]); } '; echo ' } } </script> '; echo ' <div id="map" style="width: 856px; height: 530px;"></div> '; echo "</body>"; ?> Beispiel für eine PHP-Seite mit zwei Scrollbars = abfrage_05.php <?php require_once('datenbankverbindung.php'); echo "<head>"; echo "<title>Abfrage_05</title>"; echo "<link rel='stylesheet' media='all' type='text/css' href='dortmund.css'>"; echo "<meta http-equiv='Content-Type' content='text/html; charset=iso-8859-1'>"; echo "</head>"; echo "<body>"; echo "<p class='menue'>Es wird die Luftlinienentfernung zwischen zwei"; echo " gew&auml;hlten Sehensw&uuml;rdigkeiten angezeigt.</p>"; echo "<p>&nbsp;</p>"; if (array_key_exists('sehens1',$_GET)) { $sehens1 = $_GET['sehens1']; } else { 21 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 $sehens1 = ""; } if (array_key_exists('sehens2',$_GET)) { $sehens2 = $_GET['sehens2']; } else { $sehens2 = ""; } if ($sehens1 != "" AND $sehens2 != "") { echo "<p class='untermenue'>Sie haben die Sehensw&uuml;rdigkeiten $sehens1"; echo " und $sehens2 ausgew&auml;hlt.</p>"; $query1 = "SELECT name, x, y FROM sehenswuerdigkeiten WHERE name='$sehens1'" ."ORDER BY name"; $result1 = mysql_query($query1) OR die("Mist! ". mysql_error()); $query2 = "SELECT name, x, y FROM sehenswuerdigkeiten WHERE name='$sehens2'" ."ORDER BY name"; $result2 = mysql_query($query2) OR die("Mist! ". mysql_error()); } else { echo "<p class='untermenue'>Bitte w&auml;hlen Sie zwei"; echo " Sehensw&uuml;rdigkeiten!</p>"; } /*Formular*/ echo "<form action='' method='submit'>"; echo "<select name='sehens1' size='1'>"; $query = "SELECT DISTINCT name FROM sehenswuerdigkeiten ORDER BY name"; $result = mysql_query($query); if ($result) { $rows = mysql_num_rows($result); $cols = mysql_num_fields($result); for($r=0; $r< $rows; $r++) { for($c=0; $c<$cols; $c++) { echo mysql_result($result, $r, $c), ", "; echo "<option name='sehens1'>"; echo mysql_result($result, $r, $c); echo "</option>"; } } } else { echo "Fehler"; } echo "</select>"; echo " "; echo "<select name='sehens2' size='1'>"; $query = "SELECT DISTINCT name FROM sehenswuerdigkeiten ORDER BY name"; $result = mysql_query($query); if ($result) { $rows = mysql_num_rows($result); $cols = mysql_num_fields($result); for($r=0; $r< $rows; $r++) { for($c=0; $c<$cols; $c++) { echo mysql_result($result, $r, $c), ", "; echo "<option name='sehens2'>"; echo mysql_result($result, $r, $c); echo "</option>"; } } 22 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 } else { echo "Fehler"; } echo "</select>"; echo "<input type='submit' value='OK'>"; echo "</form>"; /*Abfrage*/ if ($sehens1 != "" AND $sehens2 != "") { $objekt1 = mysql_fetch_object($result1); $objekt2 = mysql_fetch_object($result2); if ($objekt1->name != $objekt2->name) { echo "<p>Der Abstand zwischen den Sehensw&uuml;rdigkeiten <br>"; echo "<span class='dick'>".$objekt1->name."</span> und "; echo "<span class='dick'>".$objekt2->name."</span> betr&auml;gt: "; $abstand = ROUND(sqrt(pow($objekt1->x-$objekt2->x,2)+ pow($objekt1->y-$objekt2->y,2))/1000,2); echo "<br><span class='dick'>"; echo $abstand; echo " km</span></p>"; } elseif ($objekt1->name = $objekt2->name) { echo "<p>Sie haben die gleichen Sehensw&uuml;rdigkeiten gew&auml;hlt."; echo "<br>Bitte versuchen Sie es noch einmal!</p>"; } $objekt1 = mysql_fetch_object($result1); $objekt2 = mysql_fetch_object($result2); } else { echo ""; } echo "</body>"; ?> JavaScript Die Bemerkungen zu PHP gelten weitgehend auch für JavaScript, insbesondere was zur Verwendung von { und } und zu den Einrückungen dargestellt wurde. JavaScript-Programmteile dürfen keine php-Dateien aufrufen, da JavaScript auf dem Client läuft, PHP aber nur auf dem Server laufen soll. Leeren Sie einmal "C:\Dokumente und Einstellungen\<name>\Lokale Einstellungen\Temporary Internet Files". Dort steht alles, was Ihr Browser so nach und nach aus dem Netz bezogen hat. Dort dürfen keine php-Dateien zu finden sein. Google Maps mit JavaScript Ihr Datenbankprojekt soll auch Karten zeigen. In den vergangenen Semestern wurde es meist so gemacht, daß geeignete Karten gescannt und eingebunden wurden, um dann bei der Vorführung Ihres Projektes auf dem lokalen Rechner präsentiert zu wurden. Ihre Projektarbeit insgesamt kann wegen der Urheberrechte an den Kartenauszügen so nicht ins Netz gestellt werden. Und der Behelf, statt einer Karte nur eine graue Fläche zu zeigen, ist nicht sehr cool. Daher sollten Sie sich die Arbeit, 23 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 Karten zu scannen, sparen und statt dessen mit Google-Maps Ihr eigenes Projekt bereichern. Die folgende Internetadresse bietet zu allen Features einfache, gut nachvollziehbare Beispiele: http://www.google.com/apis/maps/documentation Auch hier gibt es gute Beispiele: http://kgblog.de/googlemaps/ Eine vollständige Referenz finden Sie unter: http://www.google.com/apis/maps/documentation/reference.html Google-Koordinaten Google verwendet geographische Koordinaten; also Länge (longitude) und Breite (latitude). Bei Google wird es immer in der Reihenfolge latitude, longitude eingesetzt. Wenn Sie geographische Koordinaten erfassen müssen, finden Sie Hilfe unter http://itouchmap.com/latlong.html. Wenn Sie eine andere Adresse verwenden, achten Sie darauf, daß Sie die Koordinaten bequem kopieren können, nämlich beide Werte mit einem Kopiervorgang. Beispiel 1 = GoogleMap.html Das Beispiel 1 zeigt die Verwendung von GoogleMaps ohne Zugriff auf die Datenbank mittels PHP. <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head> <meta http-equiv="content-type" content="text/html; charset=utf-8"/> <title>Google Maps JavaScript API Example</title> <script src="http://maps.google.com/maps?file=api&amp;v=2&amp;key=ABQIAAAAzosMcEBJXrsEQFGBQ AWclRQgU1QyBe_kcGDWdfFXsq08_1MSqxREpHLDVDDm5p9ub3kwCQeYethC1w" type="text/javascript"></script> <script type="text/javascript"> //<![CDATA[ /* /* /* /* /* /* /* function load() { function createListener (marker, text) { GEvent.addListener(marker, "click", function() { marker.openInfoWindowHtml(text); }); } Ausführen, nur wenn der Browser für GoogleMaps geeignet ist */ if (GBrowserIsCompatible()) { Einbindung in das <div>-Element unten*/ var map = new GMap2(document.getElementById("map")); Skalieren und Verschieben ermöglichen*/ map.addControl(new GSmallMapControl()); Auswahl von G_NORMAL_MAP, G_SATELLITE_MAP, G_HYBRID_MAP ermöglichen */ map.addControl(new GMapTypeControl()); Maßstabsleiste zeigen */ map.addControl(new GScaleControl()); Übersicht zeigen */ map.addControl(new GOverviewMapControl()); Mittelpunkt, Zoom-Level und Map-Type */ 24 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 map.setCenter(new GLatLng(51.51611, 7.46805), 11, G_NORMAL_MAP); /* Öffnen eines Info-Fensters */ map.openInfoWindow(map.getCenter(), document.createTextNode("Hier sei das Zentrum von Dortmund!")); /* Vereinbarung und Plazierung von Markern*/ var point = new Array(); var text = new Array(); point[0] = new GLatLng(51.51350, 7.46500); text[0] = "Text mit <b>Hervorhebung</b>"; point[1] = new GLatLng(51.51200, 7.46500); text[1] = "weiterer Text"; point[2] = new GLatLng(51.51200, 7.46350); text[2] = "Text mit &Auml; und &auml; und &szlig;"; point[3] = new GLatLng(51.51350, 7.46350); text[3] = "und so weiter!"; var marker = new Array(); for (i=0; i< point.length; i++) { marker[i] = new GMarker(point[i]); map.addOverlay(marker[i]); createListener (marker[i], text[i]); } } } //]]> </script> </head> <body border="0" onload="load()" onunload="GUnload()"> <div id="map" style="width: 937px; height: 720px;"></div> </body> </html> Beispiel 2 = GoogleMap2.php Das Beispiel 2 enthält in Erweiterung des Beispiels 1 zusätzlich den PHP-Zugriff auf die Datenbank, die Umrechnung von Gauß-Krüger-Koordinaten in geographische Koordinaten und die Erzeugung von JavaScript mit PHP. Das ist ein typisches Beispiel für "mash up"! <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head> Beginn XHTML <meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1" /> <title>Dortmund</title> <link href="dortmund.css" rel="stylesheet" type="text/css" /> <script src="http://maps.google.com/maps?file=api&amp;v=2&amp;key=ABQIAAAAzosMcEBJXrsEQFGBQ AWclRQgU1QyBe_kcGDWdfFXsq08_1MSqxREpHLDVDDm5p9ub3kwCQeYethC1w" type="text/javascript"> 25 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 </script> <?php Beginn PHP /* Datenbankverbindung Aufbau */ include 'datenbankverbindung.php'; $lat = "51.51350"; $long = "7.46500"; $bezeichnung = "Willkommen in Dortmund!"; $zoom = "15"; $xlow = 300000; $xhigh = 500000; $ylow = 5600000; $yhigh = 5800000; /* SQL-Anfrage */ $query = " Beginn SQL SELECT x, y, name FROM sehenswuerdigkeiten WHERE x BETWEEN $xlow AND $xhigh AND y BETWEEN $ylow AND $yhigh; "; Ende SQL /* Ausführen der SQL-Anfrage */ $result = mysql_query($query); if ($result) { $rows = mysql_num_rows($result); $cols = mysql_num_fields($result); for($r=0; $r< $rows; $r++) { $xobj[$r] = mysql_result($result, $r, 0); $yobj[$r] = mysql_result($result, $r, 1); $nobj[$r] = mysql_result($result, $r, 2); } } else { echo "Fehler"; } /* Berechnung von GK nach WGS84*/ include './gaussk.php'; for($r=0; $r< $rows; $r++) { $xin=$xobj[$r]; $yin=$yobj[$r]; $wgs84array = CalcStart($xin, $yin); $xobj[$r] = $wgs84array[0]; $yobj[$r] = $wgs84array[1]; } /* Freigeben des Resultsets, d.h. Leeren des Speichers der Variable $result */ mysql_free_result($result); echo '<script type="text/javascript">'; Beginn Erzeugung JavaScript mit PHP echo ' ab hier ein Schnipsel reines JS function load() { function createListener (marker, text) { GEvent.addListener(marker, "click", function() { marker.openInfoWindowHtml(text); } 26 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 ); } if (GBrowserIsCompatible()) { var map = new GMap2(document.getElementById("map")); map.addControl(new GSmallMapControl()); map.addControl(new GMapTypeControl()); map.addControl(new GScaleControl()); map.addControl(new GOverviewMapControl()); vor dem Hochkomma endet der Schnipsel JS echo ' Beginn JS '; map.setCenter(new GLatLng('.$lat.', '.$long.'), '.$zoom.'); var point = new Array(); var text = new Array(); var marker = new Array(); '; Ende JS, $lat, $long, $zoom for ($r=0; $r<$rows; $r++) { oben sind aber eingebettetes PHP echo ' Beginn JS wieder mit eingebettetem PHP point['.$r.'] = new GLatLng('.$xobj[$r].','.$yobj[$r].'); text['.$r.'] = "'.$nobj[$r].'"; Ende JS '; } echo ' Beginn JS var marker = new Array(); for (i=0; i< point.length; i++) { marker[i] = new GMarker(point[i]); map.addOverlay(marker[i]); createListener (marker[i], text[i]); } Ende JS echo ' Beginn JS '; } } </script> '; ?> Ende des JS-Skripts Ende PHP </head> <body border="0" onload="load()" onunload="GUnload()"> <div id="map" style="width: 937px; height: 720px;"></div> </body> </html> Ende XHTML Beispiel 3 Hier wird die Nutzung von Google Maps ohne eigenen Google-Schlüssel gezeigt. <script src="http://maps.google.com/maps?file=api&amp;v=2" type="text/javascript"> </script> <?php include("dbconnect.php"); echo "<p>Bitte w&auml;hlen Sie einen Point-of-Interest aus:<br>"; echo "<form method=\"post\">"; echo "<select name=\"poi\">"; $abfrage = "SELECT pid, name FROM poi ORDER BY name;"; 27 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 $ergebnis = mysql_query($abfrage) or die ("Fehler! ".mysql_error()); while($row = mysql_fetch_object($ergebnis)) { echo "<option value=".$row->pid.">".utf8_encode($row->name)."</option>"; } echo "</select>"; echo "<input type=\"submit\" value=\"OK\">"; echo "</form></p>"; mysql_free_result($ergebnis); if (array_key_exists("poi",$_POST)) { $poi = $_POST["poi"]; $abfrage = "SELECT name, x_geo, y_geo, typ FROM poi WHERE pid=".$poi.";"; $ergebnis = mysql_query($abfrage) or die ("Fehler! ".mysql_error()); while ($row = mysql_fetch_object($ergebnis)) { $n_poi=utf8_encode($row->name); $x_poi=$row->x_geo; $y_poi=$row->y_geo; $t_poi=utf8_encode($row->typ); } mysql_free_result($ergebnis); echo "<script type=\"text/javascript\"> function initialize() { if (GBrowserIsCompatible()) { var map = new GMap2(document.getElementById(\"map_canvas\")); map.setCenter(new GLatLng(".$y_poi.", ".$x_poi."), 12); map.addControl(new GLargeMapControl()); map.addControl(new GOverviewMapControl()); map.addControl(new GMapTypeControl()); map.enableContinuousZoom(); var point = new GMarker(new GLatLng(".$y_poi.", ".$x_poi.")); var text = \"<p>»".$n_poi."«<br>(".$t_poi.")</p>\"; GEvent.addListener(point, \"click\", function() { point.openInfoWindowHtml(text) }); map.addOverlay(point); } } </script>"; } ?> <body onload="initialize()" onunload="GUnload()"> <p> <div id="map_canvas" style="width:900px; height:500px"></div> </p> </body> Fehlersuche Im Beispiel 2 sind folgende Sprachen miteinander "verwurschtelt" (mash up): PHP, XHTML, SQL, JaveScript. Das macht die Erstellung ziemlich fehleranfällig und Sie sollten sich von Beginn an damit vertraut machen, wie Sie Fehler lokalisieren können. Als erstes muß PHP fehlerfrei sein. Das überprüfen Sie, indem Sie sich das Apache-Fehler-Log xampp/apache/logs/error.log ansehen. Sobald PHP fehlerfrei ist, muß als nächstes auch das erzeugte Javaskript fehlerfrei sein. Das Javaskript können Sie sich ansehen, indem Sie sich vom entsprechenden Frame den Quelltext zeigen lassen. Er sollte die Struktur aus Beispiel 1 haben. Fehler im Javaskript 28 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 werden im Browser in der Fehler-Konsole angezeigt. Firefox: Extras-->FehlerKonsole; IE: im Frame rechtsklicken und "Quelltext anzeigen" wählen. Übrigens: Damit das Javaskript besser lesbar ist, wurden im Beispiel 2 einige an sich überflüssige echo-Zeilen eingefügt. Projektanalyse Hamburg Meike Landmann Kontakt (?): Meike Landmann <[email protected]> 2000 WS Unterlagen Digitale Dokumentation, digitaler Netzplan, digitale Karten fehlen. Koordinaten sind wahrscheinlich Tischkoordinaten. Tabellen Tabellen sind als sql-Dateien vorhanden. Bisweilen liegt auch die Datenbank vor. Dann muß geprüft werden, was aktueller ist; in der Regel ist es wohl die Datenbank. Zeilen in „Linien“: 11 In starker Auswahl sind 11 Linien von U-Bahn, S-Bahn, Bus, Fähre und AKN(?) vorhanden. Es müssen die Spalten „von“ und „nach“ entfernt werden. CREATE TABLE linien (linie_id NUMBER(2), name CHAR(3), verkehrsmittel CHAR(6), fahrrad CHAR(4), von CHAR(20), nach CHAR(20)); INSERT INTO linien VALUES (1,'U1','U-Bahn','ja','Norderstedt Mitte','Großhansdorf'); Zeilen in „Haltestellen“: 69 CREATE TABLE haltestellen (halte_id NUMBER(2), name CHAR(25), x_koord NUMBER(5), y_koord NUMBER(5), zone NUMBER(3)); INSERT INTO haltestellen VALUES (5,'Norderstedt Mitte',20000,24800,503); Zeilen in „Haltelinien“: 92 Haltelinien hat nur das Attribut ordnungsnr. Die beiden übrigen (räumlich und zeitlich) ergänzen CREATE TABLE haltelinien (linie_id NUMBER(2), halte_id NUMBER(2), ordnungsnr NUMBER(2)); INSERT INTO haltelinien VALUES (1,5,1); Zeilen in „park_ride“: 19 CREATE TABLE park_ride (halte_id NUMBER(2), parkplaetze NUMBER(3)); Zeilen in „kundenbueros“: 15 CREATE TABLE kundenbueros (halte_id NUMBER(2), woche_auf NUMBER(2), woche_zu NUMBER(2), sa_auf NUMBER(2), sa_zu NUMBER(2), so_auf NUMBER(2), so_zu NUMBER(2), eingang CHAR (25)); Zeilen in „Fahrzeiten“: 80 Entsprechen zeitlich. In haltelinien integrieren. CREATE TABLE fahrzeiten (linie_id NUMBER(2), start_id NUMBER(2), ziel_id NUMBER(2), fahrzeit NUMBER(2)); 29 Prof. Hans Kern Kartographie und Geomatik Praktikum Datenbanken und Informationssysteme Arbeitsanleitung für das SS09 Zeilen in „tarife“: 3. Beziehung zu zone fehlt. CREATE TABLE tarife (bereich CHAR(20), kind NUMBER(4,2), erw NUMBER(4,2)); INSERT INTO tarife VALUES ('Nahbereich',1.60,2.70); Abfragen Insgesamt 12 meist recht einfache, menügetriebene Abfragen -m- MENÜ (Ihre augenblickliche Position) -1- Initialisierung der Tabellen -2- Ausgabe aller Tabellen -3- Haltestellen an einer Linie Ihrer Wahl -4- Linien an Ihrer Haltestelle -5- Haltestellen im Nahbereich Ihrer Haltestelle -6- Haltestellen im Umkreis von 2 km von Ihrer Haltestelle -7- Anzahl der P+R Parkplätze an Ihrer Haltestelle -8- Öffnungszeiten des Kundenbüros an Ihrer Haltestelle -9- Ausgabe aller Umsteigestationen -10- Berechnung der Fahrstrecke zwischen zwei Haltestellen -11- Berechnung der Fahrzeit zwischen zwei Haltestellen -12- Berechnung des Fahrpreises zwischen zwei Haltestellen für Anzahl Erwachsene und Anzahl Kinder Fazit Digitale Dokumentation, digitaler Netzplan, digitale Karten fehlen. Struktur der Tabellen muß verändert werden. Erweiterungen des Netzes sollten durchgeführt werden. Abfragen sind mit bis zu 4 Parametern versehen. 30