Skip to content

5. Verwaltung der Benutzeroberfläche

5.1. Introduction

In der Client-Server-Beziehung im Web übermittelt der Client Informationen in Form einer Parameterzeichenfolge an den Server. In unseren bisherigen Beispielen haben wir diese Zeichenfolge meist manuell erstellt, indem wir URLs der Form aufgerufen haben. In der Praxis stammen die Informationen, die der Client an den Server übermittelt, aus Formularen, die der Benutzer ausgefüllt hat. In diesem Kapitel befassen wir uns mit deren Erstellung. Außerdem stellen wir das Tool WebMatrix vor, mit dem wir Benutzeroberflächen entwerfen können. Die Installation dieses Tools wird im Anhang beschrieben.

5.2. Die Sprache HTML

5.2.1. Ein Beispiel

Betrachten wir das folgende Beispiel, das mit [Web Matrix] erstellt wurde und Folgendes enthält:

  • ein Bild
  • ein Bild
  • einen Link

Image

Starten wir [WebMatrix] und wählen wir anschließend die Option [File/New File]:

Image

Wir entscheiden uns, eine Seite mit dem Namen HTML zu erstellen. Die oben genannten Angaben führen zur Erstellung einer Datei mit dem Namen [d:\data\devel\aspnet\chap4\exemple1\exemple1.htm]. [WebMatrix] bietet zwei Möglichkeiten, diese Datei zu bearbeiten: den Modus [Design] und den Modus [HTML]:

Image

Der Modus [Design] ermöglicht die Verwendung der von [WebMatrix] angebotenen Komponentenpalette HTML:

Image

Um ein Element aus dieser Palette einzufügen, genügt es, darauf zu doppelklicken und es anschließend im Fenster [Design] zu positionieren. Der Modus [HTML] ermöglicht es, das Dokument HTML mithilfe eines Texteditors zu erstellen. Dazu muss man die Syntax der Sprache HTML kennen. Auf der Registerkarte [HTML] wurde ein Dokumentgerüst generiert:

Image

Das Fenster „[HTML]“ ist sehr hilfreich für alle, die die Sprache „HTML“ nicht beherrschen. Er erstellt sein Dokument im Fenster [Design] und überprüft den generierten HTML-Code im Fenster [HTML]. Auf diese Weise eignet er sich nach und nach die Beherrschung von HTML an und kann schon recht schnell ausschließlich mit dem Texteditor arbeiten, ohne auf den Modus [Design] zurückgreifen zu müssen. Wir werden nun zeigen, wie das zu Beginn dieses Abschnitts vorgestellte Dokument HTML erstellt wird. Wir arbeiten im Fenster [Design]. Zunächst geben wir die erste Textzeile direkt ein:

Image

  • Wir fügen die Komponente [Horizontal Rule] aus der Komponentenpalette hinzu:

Image

  • Wir fügen die Komponente [Table] hinzu:

Image

  • Wir setzen den Cursor in die dritte Zeile der Tabelle, um sie mit der Option [HTML/Edit Table/Delete Table Row] zu löschen. Anschließend geben wir den gewünschten Text in jede Zelle ein:

Image

  • Wir setzen den Cursor in eine der Zellen der Tabelle und sehen uns deren Eigenschaften an. Das Eigenschaftenfenster wird unten rechts in der Arbeitsumgebung angezeigt:

Image

  • Die Zelle wird durch das Tag HTML <TD> dargestellt. Es werden uns also die Eigenschaften des Tags <TD> angezeigt. Wir betrachten die Tabelle, die ein übergeordnetes Objekt der Zelle ist. Wir klicken auf die Dropdown-Liste (click to see parent HTML elements) oben, um das Objekt <TABLE> auszuwählen:

Image

  • Das Objekt <TABLE> verfügt über eine Eigenschaft [border], die die Breite des Rahmens um die Zellen der Tabelle festlegt. Hier wählen wir border=1.

Image

  • Wir bearbeiten nun die Attribute des Objekts <TD> der Zelle (1,2), um align=Center und width=200 (Pixel) festzulegen. Der Text wird in der Zelle zentriert (align=center) und die Zelle ist 200 Pixel breit. Um die Änderung zu sehen, müssen Sie manchmal die Registerkarte [HTML] auswählen und dann zur Registerkarte [Design] zurückkehren:

Image

  • Nun fügen wir den Text ein, der vor dem Bild steht:

Image

  • Anschließend fügen wir das Bild ein, indem wir auf die Komponente „[image]“ in der Palette doppelklicken:

Image

  • Wir wählen das Bild aus, um seine Eigenschaften zu bearbeiten:

Image

  • Im Attribut [src] geben wir den Namen der Datei ein, die das Bild enthält, hier [univ01.gif]:

Image

  • Wir fügen den Text vor dem Link ein:

Image

  • Wir machen aus dem Text „[ici]“ einen Link zur URL „[http://istia.univ-angers.fr]“. Dazu markieren wir ihn und wählen dann die Option „[HTML/Insert Hyperlink]“:

Image

  • Wir erhalten folgendes Ergebnis:

Image

  • Wir sind fast am Ziel. Sehen wir uns den generierten Code HTML auf der Registerkarte [HTML] an:
<html>
<head>
</head>
<body>
    <p>
        Le langage HTML - 1 
    </p>
    <hr />
    <table border="1">
        <tbody>
            <tr>
                <td>
                    cellule(1,1)</td>
                <td align="middle" width="200">
                    cellule(1,2)</td>
                <td>
                    cellule(1,3)</td>
            </tr>
            <tr>
                <td>
                    cellule(2,1)</td>
                <td>
                    cellule(2,2)</td>
                <td>
                    cellule(2,3)</td>
            </tr>
        </tbody>
    </table>
    <p>
        Une image <img src="univ01.gif" /> 
    </p>
    <p>
        Le site de l'istia <a href="http://istia.univ-angers.fr">ici</a>
    </p>
</body>
</html>

Es sind noch einige Details zu klären. Zunächst möchten wir unserem Dokument einen Titel geben. [WebMatrix] lässt dies im Modus [Design] nicht zu. Auf der Registerkarte [HTML] ersetzen wir die Sequenz <head>..</head> durch die folgende Sequenz:

<head>
    <title>HTML1</title>
</head>

Außerdem möchten wir den Text [Le langage HTML - 1] in größerer Schrift darstellen. Mit der Sequenz <Hi>Text</Hi> lässt sich die Schriftgröße festlegen, wobei i von 1 bis 6 variiert, von der größten bis zur kleinsten Schriftgröße. Hier wählen wir H2. Die Sequenz

    <p>
        Le langage HTML - 1 
    </p>

wird zu:

<h2>Le langage HTML - 1</h2>

Das Fenster [Design] spiegelt unsere Änderungen wider:

Image

Nun müssen wir nur noch mit der Option [View/Start] oder [F5] testen. [WebMatrix] benötigt einige Angaben, um den Webserver [Cassini] zu starten:

Image

Wir können die vorgeschlagenen Standardwerte übernehmen. Der Server [Cassini] wird gestartet und unsere Seite in einem Browser angezeigt:

Image

Aus Neugier können wir überprüfen, mit welchen Parametern [Cassini] gestartet wurde:

Image

Wir haben die Grundlagen zur Erstellung einer HTML-Seite mit [WebMatrix] vorgestellt. Der Leser ist eingeladen, weitere HTML-Seiten zu erstellen und jedes Mal den generierten HTML-Code zu überprüfen. Nach und nach wird er in der Lage sein, eine Seite ohne die Hilfe des Modus [Design] zu erstellen. Ein HTML-Dokument hat im Allgemeinen folgende Form:

<html>
    <head>
        <title>Un titre</title>
        ...
    </head>
    <body attributs>
        ...
    </body>
</html>

Das gesamte Dokument wird von den Tags <html>...</html> umschlossen. Es besteht aus zwei Teilen:

<head>...</head>: Dies ist der nicht sichtbare Teil des Dokuments. Er enthält Informationen für den Browser, der das Dokument anzeigen wird. Oft findet man hier das Tag <title>...</title>, das den Text festlegt, der in der Titelleiste des Browsers angezeigt wird. Außerdem können hier weitere Tags vorkommen, insbesondere solche, die die Schlüsselwörter des Dokuments definieren – Schlüsselwörter, die anschließend von Suchmaschinen verwendet werden. In diesem Teil können sich auch Skripte befinden, die meist in JavaScript oder VBScript geschrieben sind und vom Browser ausgeführt werden.

<body-Attribute>...</body>: Dies ist der Teil, der vom Browser angezeigt wird. Die in diesem Teil enthaltenen Tags HTML geben dem Browser die „gewünschte“ visuelle Darstellung des Dokuments vor. Jeder Browser interpretiert diese Tags auf seine eigene Weise. Zwei Browser können daher ein und dasselbe Webdokument unterschiedlich darstellen. Dies ist in der Regel eine der Herausforderungen für Webdesigner.

Der Code HTML des vorherigen Dokuments lautete wie folgt:

<html>
<head>
    <title>HTML1</title>
</head>
<body>
    <h2>Le langage HTML - 1 
    </h2>
    <hr />
    <table border="1">
        <tbody>
            <tr>
                <td>
                    cellule(1,1)</td>
                <td align="middle" width="200">
                    cellule(1,2)</td>
                <td>
                    cellule(1,3)</td>
            </tr>
            <tr>
                <td>
                    cellule(2,1)</td>
                <td>
                    cellule(2,2)</td>
                <td>
                    cellule(2,3)</td>
            </tr>
        </tbody>
    </table>
    <p>
        Une image <img src="univ01.gif" /> 
    </p>
    <p>
        Le site de l'istia <a href="http://istia.univ-angers.fr">ici</a> 
    </p>
</body>
</html>
Element
Tags und Beispiele HTML
titre du document
<title>HTML1</title>
HTML1 wird in der Titelleiste des Browsers angezeigt, der das Dokument anzeigt
barre horizontale
<hr>: Zeigt einen horizontalen Strich an
tableau
<Tabellenattribute>....</table>: zum Definieren der Tabelle
<tr Attribute>...</tr>: zum Definieren einer Zeile
<td Attribute>...</td>: zum Definieren einer Zelle
Beispiele:
<table border="1">...</table>: Das Attribut „border“ legt die Dicke des Tabellenrandes fest
<td align="center" width="200">Zelle(1,2)</td>: Definiert eine Zelle, deren Inhalt „cellule(1,2)“ lautet. Dieser Inhalt wird horizontal zentriert (align="center"). Die Zelle hat eine Breite von 200 Pixeln (width="200")
image
<img src="univ01.gif" />: Definiert ein Bild, dessen Quelldatei univ01.gif auf dem Webserver ist (src="univ01.gif"). Dieser Link befindet sich in einem Webdokument, das mit der Datei „URL“ unter http://localhost/exemple1.htm erstellt wurde. Daher fordert der Browser die Datei „URL“ unter http://localhost/univ01.gif an, um das hier referenzierte Bild abzurufen.
lien
<a href="http://istia.univ-angers.fr">hier</a>: bewirkt, dass der Text ici als Link zu http://istia.univ-angers.fr dient.

An diesem einfachen Beispiel wird deutlich, dass der Browser zur Erstellung des gesamten Dokuments zwei Anfragen an den Server stellen muss:

http://localhost/exemple1.htm, um den Quelltext HTML des Dokuments abzurufen

http://localhost/univ01.gif, um das Bild univ01.gif abzurufen

5.2.2. Erstellung eines Formulars

Ein Formular HTML dient dazu, dem Benutzer eine Seite zur Eingabe von Informationen anzuzeigen, ähnlich wie die Eingabeformulare unter Windows. Das Eingabeformular wird in Form eines Dokuments HTML an den Browser gesendet. Dieser zeigt dem Benutzer das Formular an, der es ausfüllt und über eine entsprechende Schaltfläche absendet. Der Browser übermittelt daraufhin die eingegebenen Werte zur Verarbeitung an den Server. Dabei wird nicht das gesamte Formular an den Server zurückgesendet, sondern nur die eingegebenen Werte. Das folgende Beispiel zeigt ein Webformular, das ebenfalls mit WebMatrix erstellt wurde:

Image

Der von [WebMatrix] generierte Code HTML lautet wie folgt:


<html>
    <head>
        <title>Formulaire</title>
        <script language="javascript">
        function effacer(){
            alert("Vous avez cliqué sur le bouton [Effacer]");
        }
        </script>
    </head>
    <body>
        <p>
            Gestion d'un formulaire
        </p>
        <hr />
        <form name="formulaire" method="post">
            <table border="1">
                <tr>
                    <td>
                        Etes-vous marié(e)</td>
                    <td>
                        <p align="center">
                            <input type="radio" value="oui" name="rdMarie" />Oui 
                            <input type="radio" checked value="non" name="rdMarie" />Non
                        </p>
                    </td>
                </tr>
                <tr>
                    <td>
                        Cases à cocher
                    </td>
                    <td>
                        <p align="center">
                            <input type="checkbox" value="un" name="C1" />1
                            <input type="checkbox" checked value="deux" name="C2" />2
                            <input type="checkbox" value="trois" name="C3" />3
                        </p>
                    </td>
                </tr>
                <tr>
                    <td>
                        Champ de saisie</td>
                    <td>
                        <p align="center">
                            <input type="text" maxlength="30" value="qqs mots" name="txtSaisie" />
                        </p>
                    </td>
                </tr>
                <tr>
                    <td>
                        Mot de passe</td>
                    <td>
                        <p align="center">
                            <input type="password" maxlength="12" size="12" value="unMotDePasse" name="txtMdp" />
                        </p>
                    </td>
                </tr>
                <tr>
                    <td>
                        Boîte de saisie</td>
                    <td>
                        <p align="center">
                        </p>
                        <textarea name="areaSaisie">ligne1
ligne2</textarea>
                    </td>
                </tr>
                <tr>
                    <td>
                        ComboBox</td>
                    <td>
                        <p align="center">
                        </p>
                        <select name="cmbValeurs">
                            <option value="1">choix1</option>
                            <option value="2" selected>choix2</option>
                            <option value="3">choix3</option>
                        </select>
                    </td>
                </tr>
                <tr>
                    <td>
                        Liste à choix simple</td>
                    <td>
                        <p align="center">
                        </p>
                        <select size="3" name="lstSimple">
                            <option value="1" selected>liste1</option>
                            <option value="2">liste2</option>
                            <option value="3">liste3</option>
                            <option value="4">liste4</option>
                            <option value="5">liste5</option>
                        </select>
                    </td>
                </tr>
                <tr>
                    <td>
                        Liste à choix multiple</td>
                    <td>
                        <p align="center">
                        </p>
                        <select multiple size="3" name="lstMultiple">
                            <option value="1" selected>multiple1</option>
                            <option value="2">multiple2</option>
                            <option value="3" selected>multiple3</option>
                            <option value="4">multiple4</option>
                            <option value="5">multiple5</option>
                        </select>
                    </td>
                </tr>
                <tr>
                    <td>
                        Bouton simple</td>
                    <td>
                        <p align="center">
                            <input onclick="effacer()" type="button" value="Effacer" name="btnEffacer" />
                        </p>
                    </td>
                </tr>
                <tr>
                    <td>
                        Bouton submit</td>
                    <td>
                        <p align="center">
                            <input type="submit" value="Envoyer" name="btnEnvoyer" />
                        </p>
                    </td>
                </tr>
                <tr>
                    <td>
                        Bouton reset</td>
                    <td>
                        <p align="center">
                            <input type="reset" value="Rétablir" name="btnRetablir" runat="server" />
                        </p>
                    </td>
                </tr>
            </table>
            <input type="hidden" name="secret" value="uneValeur" />
        </form>
    </body>
</html>

Die visuelle Überprüfung <--> Tag HTML ergibt Folgendes:

Prüfung
Tag HTML
formulaire
<form name="Formular" method="post">
champ de saisie
<input type="text" maxlength="30" value="ein paar Wörter" name="txtSaisie" />
champ de saisie cachée
<input type="password" maxlength="12" size="12" value="unMotDePasse" name="txtMdp" />
champ de saisie multilignes
<textarea name="areaSaisie">Zeile 1
Zeile 2</textarea>
boutons radio
<input type="radio" value="ja" name="rdMarie" />Ja
<input type="radio" checked value="nein" name="rdMarie" />Nein
cases à cocher
<input type="checkbox" value="eins" name="C1" />1
<input type="checkbox" checked value="zwei" name="C2" />2
<input type="checkbox" value="drei" name="C3" />3
Combo
<select name="cmbValeurs">
<option value="1">Auswahl 1</option>
<option value="2" selected>Option 2</option>
<option value="3">Auswahl 3</option>
</select>
liste à sélection unique
<select size="3" name="lstSimple">
<option value="1" selected>Liste 1</option>
<option value="2">Liste 2</option>
<option value="3">Liste 3</option>
<option value="4">Liste 4</option>
<option value="5">Liste 5</option>
</select>
liste à sélection multiple
<select multiple size="3" name="lstMultiple">
<option value="1" selected>multiple1</option>
<option value="2">multiple2</option>
<option value="3" selected>multiple3</option>
<option value="4">multiple4</option>
<option value="5">multiple5</option>
</select>
champ caché
<input type="hidden" name="secret" value="uneValeur" />
bouton de type submit
<input type="submit" value="Senden" name="btnEnvoyer" />
bouton de type reset
<input type="reset" value="Zurücksetzen" name="btnRetablir" runat="server" />
bouton de type button
<input onclick="effacer()" type="button" value="Löschen" name="btnEffacer" />

Sehen wir uns diese verschiedenen Steuerelemente einmal genauer an.

5.2.2.1. Das Formular

formulaire
<form name="Formular" method="post">
balise HTML
<form name="..." method="..." action="...">...</form>
attributs
name="frmexemple": Name des Formulars
method="...": Methode, die vom Browser verwendet wird, um die im Formular erfassten Werte an den Webserver zu senden
action="..." : URL, an die die im Formular erfassten Werte gesendet werden.
Ein Webformular wird von den Tags <form>...</form> umschlossen. Das Formular kann einen Namen haben (name="xx"). Dies gilt für alle Steuerelemente, die in einem Formular vorkommen können. Dieser Name ist nützlich, wenn das Webdokument Skripte enthält, die auf Elemente des Formulars verweisen müssen. Der Zweck eines Formulars besteht darin, vom Benutzer über Tastatur oder Maus eingegebene Informationen zu sammeln und diese an eine URL des Webservers zu senden. An welche? An diejenige, die im Attribut action="URL" angegeben ist. Fehlt dieses Attribut, werden die Informationen an den Webserver des Dokuments gesendet, in dem sich das Formular befindet. Wie übermittelt ein Webclient Informationen (die im Formular enthaltenen) an einen Webserver? Das haben wir bereits ausführlich besprochen. Er kann zwei verschiedene Methoden verwenden, die als POST und GET bezeichnet werden. Das Attribut method="méthode", dessen Methode entweder GET oder POST ist, des Tags <form> gibt dem Browser vor, welche Methode zum Senden der im Formular erfassten Informationen an die durch das Attribut action="URL" angegebene Adresse URL verwendet werden soll. Wenn das Attribut method nicht angegeben ist, wird standardmäßig die Methode GET verwendet.

5.2.2.2. Eingabefeld

Image

champ de saisie
<input type="text" maxlength="30" value="ein paar Wörter" name="txtSaisie" />
<input type="password" maxlength="12" size="12" value="unMotDePasse" name="txtMdp" />
balise HTML
<input type="..." name="..." size=".." value="..">
Das `input`-Tag gibt es für verschiedene Steuerelemente. Das Attribut type ermöglicht es, diese verschiedenen Steuerelemente voneinander zu unterscheiden.
attributs
type="text": Gibt an, dass es sich um ein Eingabefeld handelt
type="password": Die Zeichen im Eingabefeld werden durch *-Zeichen ersetzt. Dies ist der einzige Unterschied zum normalen Eingabefeld. Diese Art von Steuerelement eignet sich für die Eingabe von Passwörtern.
size="12": Anzahl der im Feld sichtbaren Zeichen – verhindert nicht die Eingabe weiterer Zeichen
maxlength="30": Legt die maximale Zeichenanzahl auf 30 fest – der Browser ist dafür verantwortlich, dieses Attribut einzuhalten
name="txtSaisie": Name des Steuerelements
value="ein paar Wörter": Text, der im Eingabefeld angezeigt wird.

5.2.2.3. Mehrzeiliges Eingabefeld

Image

champ de saisie multilignes
<textarea name="areaSaisie">Zeile 1
Zeile 2</textarea>
balise HTML
<textarea ...>Text</textarea>
zeigt ein mehrzeiliges Eingabefeld an, das zunächst mit Text gefüllt ist
attributs
rows="2": Anzahl der Zeilen
cols="'20": Anzahl der Spalten
name="areaSaisie": Name des Steuerelements

5.2.2.4. Optionsfelder

Image

boutons radio
<input type="radio" value="ja" name="rdMarie" />Ja
<input type="radio" checked value="nein" name="rdMarie" />Nein
balise HTML
<input type="radio" attribut2="Wert2" ..../>Text
zeigt ein Optionsfeld mit Text daneben an.
attributs
name="rdMarie": Name des Steuerelements. Radiobuttons mit demselben Namen bilden eine Gruppe, deren Elemente sich gegenseitig ausschließen: Es kann immer nur einer davon ausgewählt werden.
value="Wert": Der dem Optionsfeld zugewiesene Wert. Dieser Wert ist nicht mit dem Text zu verwechseln, der neben dem Optionsfeld angezeigt wird. Letzterer dient lediglich der Anzeige.
checked: Ist dieses Schlüsselwort vorhanden, ist das Optionsfeld markiert, andernfalls nicht.

5.2.2.5. Kontrollkästchen

cases à cocher
<input type="checkbox" value="eins" name="C1" />1
<input type="checkbox" checked value="zwei" name="C2" />2
<input type="checkbox" value="drei" name="C3" />3

Image

balise HTML
<input type="checkbox" attribut2="Wert2" ..../>Text
zeigt ein Kontrollkästchen mit Text daneben an.
attributs
name="C1": Name des Steuerelements. Kontrollkästchen können denselben Namen haben oder auch nicht. Kontrollkästchen mit demselben Namen bilden eine Gruppe zugehöriger Kontrollkästchen.
value="Wert": dem Kontrollkästchen zugewiesener Wert. Dieser Wert ist nicht mit dem Text zu verwechseln, der neben dem Kontrollkästchen angezeigt wird. Letzterer dient lediglich der Anzeige.
checked: Ist dieses Schlüsselwort vorhanden, ist das Optionsfeld aktiviert, andernfalls nicht.

5.2.2.6. Dropdown-Liste (Combo)

Combo
<select name="cmbValeurs">
<option value="1">Auswahl1</option>
<option value="2" selected>Auswahl 2</option>
<option value="3">Option 3</option>
</select>

Image

balise HTML
<select size=".." name="..">
<option [selected="selected"] [value="valeur"]>Text</option>
...
</select>
zeigt die Texte zwischen den Tags <option>...</option> in einer Liste an
attributs
name="cmbValeurs": Name des Steuerelements.
size="1": Anzahl der sichtbaren Listenelemente. size="1" macht die Liste zu einer Combobox. Dies ist der Standardwert, wenn das Attribut [size] fehlt.
selected="selected": Wenn dieses Schlüsselwort für ein Listenelement vorhanden ist, wird dieses in der Liste als ausgewählt angezeigt. In unserem obigen Beispiel erscheint das Listenelement „choix2“ als ausgewähltes Element der Combobox, wenn diese zum ersten Mal angezeigt wird.
value="Wert": Legt den Wert fest, der an den Server gesendet werden soll, wenn das Element ausgewählt wird. Fehlt dieses Attribut, wird der mit der Option verknüpfte Text an den Server gesendet.

5.2.2.7. Liste mit einer Auswahlmöglichkeit

liste à sélection unique
<select size="3" name="lstSimple">
<option value="1" selected>Liste1</option>
<option value="2">Liste2</option>
<option value="3">Liste 3</option>
<option value="4">Liste 4</option>
<option value="5">Liste 5</option>
</select>

Image

balise HTML
<select size=".." name="..">
<option [selected] [value="valeur"]>...</option>
...
</select>
zeigt die Texte zwischen den Tags <option>...</option> in einer Liste an
attributs
– dieselben wie bei der Dropdown-Liste, die nur ein Element anzeigt. Dieses Steuerelement unterscheidet sich von der vorherigen Dropdown-Liste lediglich durch sein Attribut „size>1“.

5.2.2.8. Mehrfachauswahlliste

liste à sélection multiple
<select multiple size="3" name="lstMultiple">
<option value="1" selected>multiple1</option>
<option value="2">multiple2</option>
<option value="3" selected>multiple3</option>
<option value="4">multiple4</option>
<option value="5">multiple5</option>
</select>

Image

balise HTML
<select size=".." name=".." multiple>
<option [selected] ] [value="valeur"]>...</option>
...
</select>
zeigt die Texte zwischen den Tags <option>...</option> in einer Liste an
attributs
multiple: Ermöglicht die Auswahl mehrerer Elemente in der Liste. Im obigen Beispiel sind die Elemente liste1 und liste3 beide ausgewählt.

5.2.2.9. Schaltfläche vom Typ „button“

bouton de type button
<input onclick="effacer()" type="button" value="Löschen" name="btnEffacer" />

Image

balise HTML
<input type="button" value="..." name="..." onclick="effacer()" ....>
attributs
type="button": Definiert ein Schaltfeld. Es gibt zwei weitere Schaltfeldtypen: submit und reset.
value="Löschen": Der auf der Schaltfläche angezeigte Text
onclick="Funktion()": Ermöglicht die Definition einer Funktion, die ausgeführt werden soll, wenn der Benutzer auf die Schaltfläche klickt. Diese Funktion ist Teil der im angezeigten Webdokument definierten Skripte. Die vorstehende Syntax entspricht der Syntax javascript. Wenn die Skripte in VBScript geschrieben sind, müsste man onclick="Funktion" ohne Klammern schreiben. Die Syntax bleibt identisch, wenn Parameter an die Funktion übergeben werden sollen: onclick="Funktion(val1, val2,...)"
In unserem Beispiel ruft ein Klick auf die Schaltfläche Effacer die folgende JavaScript-Funktion effacer auf:

        <script language="javascript">
        function effacer(){
            alert("Vous avez cliqué sur le bouton [Effacer]");
        }
        </script>
Die Funktion effacer zeigt folgende Meldung an:

5.2.2.10. Schaltfläche vom Typ „Submit“

bouton de type submit
<input type="submit" value="Senden" name="btnEnvoyer" />

Image

balise HTML
<input type="submit" value="Senden" name="btnEnvoyer">
attributs
type="submit": Definiert die Schaltfläche als Schaltfläche zum Senden der Formulardaten an den Webserver. Wenn der Benutzer auf diese Schaltfläche klickt, sendet der Browser die Formulardaten an die im Attribut „action“ des Tags <form> angegebene Adresse URL gemäß der im Attribut „method“ desselben Tags definierten Methode.
value="Senden": Der auf der Schaltfläche angezeigte Text

5.2.2.11. Schaltfläche vom Typ „Reset“

bouton de type reset
<input type="reset" value="Zurücksetzen" name="btnRetablir" runat="server" />

Image

balise HTML
<input type="reset" value="Zurücksetzen" name="btnRetablir">
attributs
type="reset": Definiert die Schaltfläche als Schaltfläche zum Zurücksetzen des Formulars. Wenn der Benutzer auf diese Schaltfläche klickt, versetzt der Browser das Formular in den Zustand zurück, in dem es empfangen wurde.
value="Zurücksetzen": Der auf der Schaltfläche angezeigte Text

5.2.2.12. Verstecktes Feld

champ caché
<input type="hidden" name="secret" value="uneValeur" />
balise HTML
<input type="hidden" name="..." value="...">
attributs
type="hidden": Gibt an, dass es sich um ein verstecktes Feld handelt. Ein verstecktes Feld ist Teil des Formulars, wird dem Benutzer jedoch nicht angezeigt. Würde der Benutzer jedoch seinen Browser auffordern, den Quellcode anzuzeigen, würde er das Tag <input type="hidden" value="..."> und somit den Wert des versteckten Feldes sehen.
value="einWert": Wert des versteckten Feldes.
Wozu dient das versteckte Feld? Es ermöglicht dem Webserver, Informationen über mehrere Anfragen eines Kunden hinweg zu speichern. Betrachten wir eine Online-Shopping-Anwendung. Der Kunde kauft auf einer ersten Seite eines Katalogs einen ersten Artikel art1 in der Menge q1 und wechselt dann zu einer neuen Seite des Katalogs. Um zu speichern, dass der Kunde q1 Artikel art1 gekauft hat, kann der Server diese beiden Informationen in ein verstecktes Feld des Webformulars auf der neuen Seite einfügen. Auf dieser neuen Seite kauft der Kunde die Artikel q2 und art2. Wenn die Daten dieses zweiten Formulars an den Server gesendet werden (Submit), erhält dieser nicht nur die Informationen (q2, art2), sondern auch (q1, art1), die ebenfalls Teil des Formulars als verstecktes Feld sind, das vom Benutzer nicht geändert werden kann. Der Webserver wird dann die Informationen (q1,art1) und (q2,art2) in ein neues verstecktes Feld einfügen und eine neue Katalogseite senden. Und so weiter.

5.3. Übermittlung der Werte eines Formulars durch einen Browser an einen Webserver

Aus dem vorigen Kapitel wissen wir bereits, wie ein Client Informationen an den Server übermittelt. Dies geschieht entweder über:

  • einer Anfrage mit der URL „HTTP GET?param1=va1&param2=val2&...“
  • einer Anfrage HTT POST url, gefolgt von einem Dokument, das die Parameterfolge param1=va1&param2=val2&.... enthält.

Der Browser verwendet eine dieser beiden Methoden, je nachdem, ob das Attribut [method] des Tags [form] den Wert GET oder POST hat. Das werden wir nun zeigen. Die zuvor untersuchte Seite ist eine statische Seite. Um Zugriff auf die HTTP-Header zu erhalten, die vom Browser gesendet werden, der dieses Dokument anfordert, wandeln wir sie in eine dynamische Seite für einen Webserver .NET (IIS oder Cassini) um. Der zuvor genannte statische Code wird in eine Datei mit dem Namen [formulaire_get.aspx] eingefügt, deren Inhalt wie folgt lautet:


<%@ Page src="formulaire_get.aspx.vb" Language="vb" AutoEventWireup="false" Inherits="formulaire_get" %>
<html>
    <head>
        <title>Formulaire</title>
        <script language="javascript">
        function effacer(){
            alert("Vous avez cliqué sur le bouton [Effacer]");
        }
        </script>
    </head>
    <body>
.....
    </body>
</html>

Die oben angezeigte Übersichtsseite bezieht sich auf den Controller [formulaire_get.aspx.vb]:


Public Class formulaire_get
    Inherits System.Web.UI.Page

    Private Sub Page_Init(ByVal Sender As Object, ByVal e As System.EventArgs) Handles MyBase.Init
        ' speichert die aktuelle Abfrage in request.txt im Seitenordner
        Dim requestFileName As String = Me.MapPath(Me.TemplateSourceDirectory) + "\request.txt"
        Me.Request.SaveAs(requestFileName, True)
    End Sub
End Class

Bei jedem Aufruf des Dokuments [formulaire_get.aspx] wird die Anfrage des Kunden durch die Prozedur Page_Init in einer Datei [request.txt] gespeichert. Da wir diese Funktionsweise bereits kennen, werden wir den Controller nicht weiter erläutern.

5.3.1. Methode GET

Führen wir einen ersten Test durch, bei dem im Code HTML des Dokuments das Tag FORM wie folgt definiert ist:


        <form name="formulaire" method="get">

Wir legen die Dateien [formulaire_get.aspx] und [formulaire_get.aspx.vb] in einem Ordner <application-path> ab und starten den Cassini-Server mit den Parametern (<application-path>,/form2). Wir rufen die URL http://localhost/form2/formulaire_get.aspx auf:

Image

Der Browser hat soeben eine Anfrage gestellt, und wir wissen, dass diese in der Datei [request.txt] gespeichert wurde. Sehen wir uns deren Inhalt an:

GET /form2/formulaire_get.aspx HTTP/1.1
Cache-Control: max-age=0
Connection: keep-alive
Keep-Alive: 300
Accept: application/x-shockwave-flash,text/xml,application/xml,application/xhtml+xml,text/html;q=0.9,text/plain;q=0.8,image/png,image/jpeg,image/gif;q=0.2,*/*;q=0.1
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Accept-Encoding: gzip,deflate
Accept-Language: en-us,en;q=0.5
Host: localhost
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.7b) Gecko/20040316

Der Browser hat die Anfrage HTTP GET verwendet, um die URL [http://localhost/form2/formulaire_get.aspx] abzufragen. Dies ist immer dann der Fall, wenn die URL vom Benutzer angegeben wird. Wir füllen das Formular wie folgt aus:

Image

Wir verwenden die oben genannte Schaltfläche [Envoyer]. Ihr Code HTML lautet wie folgt:

<form method="get">
    ...
    <input type="submit" value="Envoyer">
    ...
</form>

Beim Klicken auf eine Schaltfläche vom Typ [Submit] sendet der Browser die Formularparameter (Tag <form>) an die im Attribut [action] des Tags <form action="URL"> angegebene Adresse URL, sofern diese existiert. Wenn dieses Attribut nicht vorhanden ist, werden die Formularparameter an die URL URL gesendet, von der das Formular bereitgestellt wurde. Dies ist hier der Fall. Die Schaltfläche [Envoyer] sollte daher eine Anfrage des Browsers an die Seite URL [http://localhost/form2/formulaire_get.aspx] auslösen, wobei die Formularparameter übertragen werden. Da die Seite [formulaire_get.aspx] die empfangene Anfrage speichert, sollten wir wissen, wie der Client diese Parameter übertragen hat. Versuchen wir es. Wir klicken auf die Schaltfläche [Envoyer]. Wir erhalten folgende Antwort vom Browser:

Image

Das ist die Startseite, aber man kann feststellen, dass sich der Wert „URL“ im Feld „[Adresse]“ des Browsers geändert hat. Er lautet nun wie folgt:

http://localhost/form2/formulaire_get.aspx?rdMarie=ja&C1=eins&C2=zwei&txtSaisie=Programmierung+asp.net&txtMdp=unMotDePasse&areaSaisie=die+Grundlagen+der%0D%0AWebprogrammierung%0D%0A&cmbValeurs=3&lstSimple=1&lstMultiple=2&lstMultiple=4&btnEnvoyer=Senden&secret=uneValeur

Man stellt fest, dass die im Formular getroffenen Auswahlen im Feld „URL“ wiederzufinden sind. Sehen wir uns den Inhalt der Datei „[request.txt]“ an, in der die Anfrage des Clients gespeichert wurde:

GET /form2/formulaire_get.aspx?rdMarie=oui&C1=un&C2=deux&txtSaisie=programmation+asp.net&txtMdp=ceciestsecre&areaSaisie=les+bases+de+la%0D%0Aprogrammation+web%0D%0A&cmbValeurs=3&lstSimple=1&lstMultiple=2&lstMultiple=4&btnEnvoyer=Envoyer&secret=uneValeur HTTP/1.1
Connection: keep-alive
Keep-Alive: 300
Accept: application/x-shockwave-flash,text/xml,application/xml,application/xhtml+xml,text/html;q=0.9,text/plain;q=0.8,image/png,image/jpeg,image/gif;q=0.2,*/*;q=0,1
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Accept-Encoding: gzip,deflate
Accept-Language: en-us,en;q=0.5
Host: localhost
Referer: http://localhost/form2/formulaire_get.aspx
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.7b) Gecko/20040316

Es handelt sich um eine Anfrage mit dem Namen HTTP, die der ursprünglichen Anfrage des Browsers sehr ähnlich ist, als dieser das Dokument ohne Übermittlung von Parametern angefordert hatte. Es gibt zwei Unterschiede:

GET URL HTTP/1.1
Die Formularparameter wurden hinter der Dokument-ID URL in der Form ?param1=val1&param2=val2&... hinzugefügt.
Referer
Der Kunde gibt mit diesem Header „HTTP“ die Nummer „URL“ des Dokuments an, das er gerade angezeigt hatte, als er die Anfrage stellte.

Schauen wir uns genauer an, wie die Parameter im Befehl GET URL?param1=Wert1&param2=Wert2&... übergeben wurden. HTTP/1.1, wobei die parami die Namen der Steuerelemente des Webformulars und die valeuri die ihnen zugeordneten Werte sind. Nachfolgend stellen wir eine Tabelle mit drei Spalten vor:

  • Spalte 1: enthält die Definition eines Steuerelements HTML aus dem Beispiel
  • Spalte 2: zeigt die Darstellung dieses Steuerelements in einem Browser
  • Spalte 3: zeigt den Wert an, den der Browser für das Steuerelement aus Spalte 1 an den Server sendet, und zwar in der Form, wie er in der Abfrage GET aus dem Beispiel vorliegt
Steuerelement HTML
Anzeige vor der Validierung
zurückgegebener Wert/zurückgegebene Werte
<input type="radio" value="ja" name="rdMarie" />Ja
<input type="radio" checked
value="nein" name="rdMarie" />Nein
rdMarie=ja
– der Wert des Attributs value der Schaltfläche
, das vom Benutzer ausgewählt wurde.
<input type="checkbox"
value="un" name="C1" />1
<input type="checkbox"
checked value="zwei" name="C2" />2
<input type="checkbox"
value="drei" name="C3" />3
C1=eins
C2=zwei
– Werte der Attribute value der vom Benutzer
vom Benutzer angekreuzten Kontrollkästchen
<input type="text" maxlength="30" value="qqs
Wörter" name="txtSaisie" />
txtEingabe=Programmierung+ASP.NET
– vom Benutzer in das Eingabefeld eingegebener Text
. Leerzeichen wurden
durch das Pluszeichen ersetzt
<input type="password"
maxlength="12" size="12"
value="einPasswort"
name="txtMdp" />
txtMdp=dasistgeheim
– vom Benutzer in das Eingabefeld eingegebener Text
. Der tatsächlich eingegebene Text lautete
„ceciestsecret“. Das letzte Zeichen ging
verloren gegangen, da das Attribut
maxlength="12" die Anzahl der
Zeichen auf 12 beschränkte.
<textarea name="areaSaisie">
Zeile1
Zeile 2</textarea>
Eingabebereich=die+Grundlagen+von+
der%0D%0A
Webprogrammierung
– vom Benutzer in das Eingabefeld eingegebener Text
Eingabefeld eingegeben. %OD%OA ist das Zeichen für
Zeilenende. Die Leerzeichen wurden
durch das Zeichen + ersetzt
<select name="cmbValeurs">
<option value="1">Auswahl1
</option>
<option value="2" selected>Auswahl 2
</option>
<option value="3">Auswahl 3
</option>
</select>
cmbWerte=3
- vom Benutzer in der
Liste mit einer Auswahlmöglichkeit
<select size="3"
name="lstSimple">
<option value="1"
selected>Liste1</option>
<option value="2">Liste 2
</option>
<option value="3">Liste 3
</option>
<option value="4">Liste 4
</option>
<option value="5">Liste 5
</option>
</select>
lstSimple=3
– vom Benutzer in der
Liste mit einer Auswahlmöglichkeit
<select multiple size="3"
name="lstMultiple">
<option value="1" selected>multiple1
</option>
<option value="2">multiple2
</option>
<Option Wert="3" ausgewählt>multiple3
</option>
<option value="4">multiple4
</option>
<option value="5">multiple5
</option>
</select>
lstMultiple=2
lstMultiple=4
- vom Benutzer in der
Mehrfachauswahlliste
<input type="submit"
value="Senden"
name="btnEnvoyer" />
btnEnvoyer=Senden
– Name und Attribut value der Schaltfläche, die
zum Senden der Formulardaten
an den Server
<input type="hidden"
name="secret"
value="einWert" />
 
secret=einWert
– Attribut value des versteckten Feldes

Man könnte sich fragen, was der Server mit den übergebenen Parametern gemacht hat. Tatsächlich gar nichts. Beim Empfang des Befehls

GET /form2/formulaire_get.aspx?rdMarie=oui&C1=un&C2=deux&txtSaisie=programmation+asp.net&txtMdp=ceciestsecre&areaSaisie=les+bases+de+la%0D%0Aprogrammation+web%0D%0A&cmbValeurs=3&lstSimple=1&lstMultiple=2&lstMultiple=4&btnEnvoyer=Envoyer&secret=uneValeur HTTP/1.1

Der Webserver hat die Parameter an das Dokument URL, [http://localhost/form2/formulaire_get.aspx] und c.a.d weitergeleitet, das wir ursprünglich erstellt haben. Wir haben keinen Code geschrieben, um die vom Client gesendeten Parameter abzurufen und zu verarbeiten. Daher läuft alles so ab, als ob die Anfrage des Clients einfach lauten würde:

GET http://localhost/form2/formulaire_get.aspx

Aus diesem Grund haben wir als Antwort auf unsere Schaltfläche [Envoyer] dieselbe Seite erhalten wie ursprünglich bei der Anfrage von URL und [http://localhost/form2/formulaire_get.aspx] ohne Parameter.

5.3.2. Methode POST

Das Dokument HTML ist nun so konfiguriert, dass der Browser die Methode POST verwendet, um die Formularwerte an den Webserver zu senden. Dazu kopieren wir die Datei [formulaire_get.aspx] in [formulaire_post.aspx] und ändern lediglich das Tag <form> in [formulaire_post.aspx]:


<%@ Page src="formulaire_get.aspx.vb" Language="vb" AutoEventWireup="false" Inherits="formulaire_get" %>
<html>
    <head>
        ...
    </head>
    <body>
        <p>
            Gestion d'un formulaire
        </p>
        <hr />
        <form name="formulaire" method="post">
            <table border="1">

Es besteht keine Notwendigkeit, den Controller [formulaire_get.aspx.vb] auszutauschen, daher belassen wir ihn im aktuellen Zustand. Wir fordern das neue Dokument über URL [http://localhost/form2/formulaire_post.aspx] an, füllen das Formular wie bei der Methode GET aus und übermitteln die Parameter mit der Schaltfläche [Envoyer] an den Server. Wir erhalten vom Server die folgende Antwortseite:

Image

Wir erhalten also dasselbe Ergebnis wie bei den Methoden GET und c.a.d: die Startseite. Es ist jedoch ein Unterschied zu bemerken: Im Feld [Adresse] des Browsers werden die übermittelten Parameter nicht angezeigt. Sehen wir uns nun die vom Client gesendete Anfrage an, die in der Datei [request.txt] gespeichert wurde:

POST /form2/formulaire_post.aspx HTTP/1.1
Connection: keep-alive
Keep-Alive: 300
Content-Length: 222
Content-Type: application/x-www-form-urlencoded
Accept: application/x-shockwave-flash,text/xml,application/xml,application/xhtml+xml,text/html;q=0.9,text/plain;q=0.8,image/png,image/jpeg,image/gif;q=0.2,*/*;q=0,1
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Accept-Encoding: gzip,deflate
Accept-Language: en-us,en;q=0.5
Host: localhost
Referer: http://localhost/form2/formulaire_post.aspx
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.7b) Gecko/20040316

rdMarie=oui&C1=un&C2=deux&txtSaisie=programmation+asp.net&txtMdp=ceciestsecre&areaSaisie=les+bases+de+la%0D%0Aprogrammation+web%0D%0A&cmbValeurs=3&lstSimple=3&lstMultiple=2&lstMultiple=4&btnEnvoyer=Envoyer&secret=uneValeur

In der Abfrage HTTP des Kunden tauchen neue Einträge auf:

POST URL HTTP/1.1
Die Abfrage GET wurde durch die Abfrage POST ersetzt. Die Parameter sind in dieser ersten Zeile der Abfrage nicht mehr vorhanden. Man kann feststellen, dass sie nun nach einer Leerzeile hinter der Abfrage HTTP stehen. Ihre Kodierung ist identisch mit derjenigen, die sie in der Abfrage GET hatten.
Content-Length
Anzahl der „gesendeten“ Zeichen, c.a.d. Die Anzahl der Zeichen, die der Webserver nach dem Empfang der Header HTTP lesen muss, um das vom Client gesendete Dokument abzurufen. Bei dem betreffenden Dokument handelt es sich hier um die Liste der Formularwerte.
Content-type
gibt den Typ des Dokuments an, das der Client nach den Headern HTTP sendet. Der Typ [application/x-www-form-urlencoded] gibt an, dass es sich um ein Dokument handelt, das Formularwerte enthält.

Es gibt zwei Methoden, um Daten an einen Webserver zu übermitteln: GET und POST. Gibt es eine Methode, die besser ist als die andere? Wir haben gesehen, dass, wenn die Werte eines Formulars vom Browser mit der Methode GET gesendet wurden, der Browser in seinem Feld Adresse die angeforderte URL in der Form URL?param1=val1&param2=val2&... anzeigt. Man kann dies als Vorteil oder als Nachteil betrachten:

  • ein Vorteil, wenn man dem Benutzer ermöglichen möchte, diese konfigurierte URL in seine Lesezeichen aufzunehmen
  • ein Nachteil, wenn man nicht möchte, dass der Benutzer Zugriff auf bestimmte Informationen des Formulars hat, wie zum Beispiel versteckte Felder

Im weiteren Verlauf werden wir in unseren Formularen fast ausschließlich die Methode POST verwenden.

5.4. Serverseitige Verarbeitung der Werte eines Formulars

5.4.1. Vorstellung des Beispiels

Nachdem wir nun den Zusammenhang zwischen dem Tag HTML <form method="GET/POST" ...> und der Art und Weise hergestellt haben, wie der Browser die Formularwerte übermittelt, wissen wir, wie wir diese serverseitig abrufen können. Die Antwort darauf haben wir im vorigen Kapitel erhalten:

  • Wenn die Methode des Tags <form> GET lautet, werden die Werte der Parameter in der Sammlung [Request.QueryString] abgerufen
  • Wenn die Methode des Tags <form> „POST“ lautet, werden die Werte der „gesendeten“ Parameter in der Sammlung „[Request.Form]“ abgerufen. Hier ist eine Präzisierung erforderlich. Das Tag <form> kann mithilfe des Attributs [action] die Ziel-URL von GET oder von POST angeben. Diese URL kann durchaus so konfiguriert werden, dass es sich um ein GET oder ein POST handelt, und zwar in der Form action="url?param1=val1&param2=val2&..". Diese Parameter werden dann zu denen hinzugefügt, die zwischen den Tags <form> und </form> stehen und die mittels eines GET oder eines POST an den Server übertragen werden. Da sie Teil der Ziel-URL sind, werden sie in der Sammlung [Request.QueryString] abgerufen, unabhängig davon, ob es sich um ein GET oder ein POST handelt.

Wir schreiben nun eine Anwendung MVC mit zwei Ansichten:

  • Die erste Ansicht ist das zuvor beschriebene Formular. Wir nennen sie [vue_formulaire].
  • Die zweite Ansicht ist eine Informationsseite, auf der die auf der ersten Seite eingegebenen Werte aufgelistet sind. Über einen Link gelangt man zurück zum Formular. Wir nennen diese Ansicht [vue_confirmation].

Die Ansicht [vue_formulaire] wird an den Benutzer gesendet, der sie ausfüllt und bestätigt. Sie könnte kurz vor der Bestätigung etwa so aussehen:

Image

Der Benutzer verwendet die Schaltfläche [Envoyer], um seine Eingaben zu bestätigen. Als Antwort erhält er die folgende Ansicht [vue_validation]:

Image

5.4.2. Der Controller der Anwendung

Im vorigen Kapitel haben wir gesehen, dass wir die Rolle des Controllers einer Anwendung MVC der Datei [global.asax] übertragen können, über die alle Client-Anfragen laufen. Wir haben bereits eine entsprechend aufgebaute Anwendung MVC vorgestellt und folgen hier dem damals vorgestellten Entwicklungsmodell. Die Datei [global.asax] sieht wie folgt aus:

<%@ Application src="Global.asax.vb" Inherits="Global" %>

Sie besteht aus einer einzigen Zeile, die auf den Controller in der Datei [global.asax.vb] verweist:


Imports System
Imports System.Web
Imports System.Web.SessionState

Public Class Global
    Inherits System.Web.HttpApplication

    Sub Application_BeginRequest(ByVal sender As Object, ByVal e As EventArgs)
        ' die auszuführende Aktion wird abgerufen
        Dim action As String
        If Request.QueryString("action") Is Nothing Then
            action = "init"
        Else
            action = Request.QueryString("action").ToString.ToLower
        End If
        ' die Aktion wird ausgeführt
        Select Case action
            Case "init"
                Server.Transfer("formulaire.aspx", False)
            Case "validation"
                Server.Transfer("validation.aspx", True)
            Case Else
                Server.Transfer("formulaire.aspx", True)
        End Select
    End Sub
End Class

Das Prinzip des Controllers ist wie folgt:

  • Er erwartet in der Ziel-URL eine Parameterkette, die den Parameter [action] enthält. Fehlt dieser, wird so verfahren, als wäre [action=init] in der Parameterkette enthalten.
  • Es werden nur zwei Aktionen erkannt:
    • init: Dem Kunden wird das vorausgefüllte Formular bereitgestellt
    • validation: Dem Client wird die Seite zur Bestätigung seiner Eingaben bereitgestellt
  • Wenn die Aktion keine der oben genannten ist, wird so verfahren, als wäre [action=init] vorhanden. Es könnte auch eine Fehlerseite ausgegeben werden.

5.4.3. Verarbeitung der Aktion „init“

Wenn der Controller die Aktion „init“ verarbeitet, muss er ein vorausgefülltes Formular generieren. Diese Aufgabe übernimmt die Seite [formulaire.aspx]. Ihr Code lautet wie folgt:


<HTML>
    <HEAD>
        <title>Formulaire</title>
        <script language="javascript">
        function effacer(){
            alert("Vous avez cliqué sur le bouton [Effacer]");
        }
        function raz(liste){
            liste.selectedIndex=-1
        }
        </script>
    </HEAD>
    <body>
        <p>
            Gestion d'un formulaire
        </p>
        <hr>
        <form name="formulaire" method="post" action="?action=validation">
            <table border="1">
                <tr>
                    <td>
                        Etes-vous marié(e)</td>
                    <td>
                        <p align="center">
                            <input type="radio" value="oui" name="rdMarie">Oui <input type="radio" checked value="non" name="rdMarie">Non
                        </p>
                    </td>
                </tr>
....
                    <td>
                        <select size="3" name="lstSimple">
                            <option value="1" selected>liste1</option>
                            <option value="2">liste2</option>
                            <option value="3">liste3</option>
                            <option value="4">liste4</option>
                            <option value="5">liste5</option>
                        </select>
                        <INPUT type="button" value="Raz" name="btnRazSimple" onclick="raz(lstSimple)">
                    </td>
....
                    <td>
                        <select multiple size="3" name="lstMultiple">
                            <option value="1" selected>multiple1</option>
                            <option value="2">multiple2</option>
                            <option value="3" selected>multiple3</option>
                            <option value="4">multiple4</option>
                            <option value="5">multiple5</option>
                        </select>
                        <INPUT type="button" value="Raz" name="btnRazMultiple" onclick="raz(lstMultiple)">
                    </td>
...

            </table>
            <input type="hidden" name="secret" value="uneValeur">
        </form>
    </body>
</HTML>

Wir finden den Code HTML aus dem zuvor untersuchten Formular wieder, mit einigen wenigen Unterschieden. Der Code des Tags <form> wurde geändert:


        <form name="formulaire" method="post" action="?action=validation">
  • post: Die vom Benutzer eingegebenen Werte, die bei Betätigung der Schaltfläche vom Typ [submit] an den Server gesendet werden, werden über die Methode HTTP POST übermittelt
  • action: Die Syntax action="url" dient dazu, die URL anzugeben, an die die Formularwerte gesendet werden sollen. Diese URL kann eine Parameterkette in der Form param1=val1&param2=val2&... enthalten Genau das geschieht hier, wo wir den Parameter [action=validation] übergeben, um dem Controller mitzuteilen, welche Aktion er ausführen soll. Es ist zu beachten, dass dieser Parameter-String nicht von einer Webadresse eingeleitet wird. Der Browser sendet die Formularparameter dann an die Adresse, von der er dieses Formular erhalten hat. In unserem oben dargestellten Beispiel lautet diese Adresse [http://localhost/mvcform1]. Der Browser sendet also eine Anfrage mit dem Format [POST /mvcform1?action=validation] an den Rechner [localhost].

Es wurden Schaltflächen hinzugefügt, damit der Benutzer die Auswahl der Elemente in den Listen [lstSimple] und [lstMultiple] aufheben kann:

Image

Dies führt zu folgendem Code HTML:


                    <td>
                        <select size="3" name="lstSimple">
                            <option value="1" selected>liste1</option>
                            <option value="2">liste2</option>
                            <option value="3">liste3</option>
                            <option value="4">liste4</option>
                            <option value="5">liste5</option>
                        </select>
                        <INPUT type="button" value="Raz" name="btnRazSimple" onclick="raz(lstSimple)">
                    </td>
....
                    <td>
                        <select multiple size="3" name="lstMultiple">
                            <option value="1" selected>multiple1</option>
                            <option value="2">multiple2</option>
                            <option value="3" selected>multiple3</option>
                            <option value="4">multiple4</option>
                            <option value="5">multiple5</option>
                        </select>
                        <INPUT type="button" value="Raz" name="btnRazMultiple" onclick="raz(lstMultiple)">
                    </td>

Ein Klick auf eine Schaltfläche [Raz] führt dazu, dass alle Elemente der Liste, der sie zugeordnet ist, abgewählt werden. Nehmen wir das Beispiel der Liste [lstMultiple]. Ein Klick auf die entsprechende Schaltfläche [Raz] führt zur Ausführung der JavaScript-Funktion [raz(lstMultiple)]. Zur Erinnerung: Der JavaScript-Code eines HTML-Dokuments, das von einem Browser angezeigt wird, wird von diesem Browser selbst und nicht vom Server ausgeführt. JavaScript ist eine sehr umfassende Sprache, mit der Seiten ohne Eingriff des Servers dynamisch gestaltet werden können. Die Funktion [raz] lautet wie folgt:

        function raz(liste){
            liste.selectedIndex=-1
        }

Diese Funktion erhält einen Parameter, bei dem es sich um ein JavaScript-Objekt handelt, das eine Liste HTML darstellt. Dieses Objekt verfügt über Eigenschaften und Methoden. Eine seiner Eigenschaften ist [selectedIndex], deren Wert die Nummer der ersten in der Liste HTML ausgewählten Option ist. Ist keine Option ausgewählt, hat diese Eigenschaft den Wert -1. Umgekehrt entspricht das Setzen eines Werts für diese Eigenschaft der Auswahl eines neuen Elements in der Liste HTML, und das Setzen des Werts -1 bedeutet, dass kein Element ausgewählt ist. Genau das wird hier getan.

Schließlich ist zu beachten, dass der Darstellungscode [formulaire.aspx] nicht mit einem Controller [formulaire.aspx.vb] verbunden ist. Tatsächlich enthält das Dokument HTML keinen vom Server generierten dynamischen Teil, sodass kein Controller erforderlich ist.

5.4.4. Verarbeitung der Validierungsaktion

Wenn der Controller die Aktion „Validierung“ verarbeitet, muss er eine Seite generieren, auf der die vom Benutzer eingegebenen Werte aufgelistet sind. Diese Aufgabe übernimmt die Seite [validation.aspx]. Optisch sieht die Seite wie folgt aus:

Image

Ihr Code HTML lautet wie folgt:


<%@ Page src="validation.aspx.vb" Language="vb" AutoEventWireup="false" Inherits="validation" %>
<HTML>
    <HEAD>
        <title>validation</title>
    </HEAD>
    <body>
        <P>Valeurs saisies</P>
        <HR width="100%" SIZE="1">
        <TABLE id="Table1" cellSpacing="1" cellPadding="1" width="300" border="1">
            <TR>
                <TD width="84">rdMarie</TD>
                <TD><% =rdMarie%></TD>
            </TR>
            <TR>
                <TD width="84">C1</TD>
                <TD><%=C1%></TD>
            </TR>
            <TR>
                <TD width="84">C2</TD>
                <TD><%=C2%></TD>
            </TR>
            <TR>
                <TD width="84">C3</TD>
                <TD><%=C3%></TD>
            </TR>
            <TR>
                <TD width="84">txtSaisie</TD>
                <TD><%=txtSaisie%></TD>
            </TR>
            <TR>
                <TD width="84">txtMdp</TD>
                <TD><%=txtMdp%></TD>
            </TR>
            <TR>
                <TD width="84">areaSaisie</TD>
                <TD><%=areaSaisie%></TD>
            </TR>
            <TR>
                <TD width="84">cmbValeurs</TD>
                <TD><%=cmbValeurs%></TD>
            </TR>
            <TR>
                <TD width="84">lstSimple</TD>
                <TD><%=lstSimple%></TD>
            </TR>
            <TR>
                <TD width="84">lstMultiple</TD>
                <TD><%=lstMultiple%></TD>
            </TR>
            <TR>
                <TD width="84">secret</TD>
                <TD><%=secret%></TD>
            </TR>
        </TABLE>
    </body>
</HTML>

Die dynamischen Teile <%=variable%> des Dokuments werden vom zugehörigen Controller [validation.aspx.vb] berechnet:


Imports System.Text.RegularExpressions

Public Class validation
    Inherits System.Web.UI.Page

    Protected rdMarie As String
    Protected C1 As String
    Protected C2 As String
    Protected C3 As String
    Protected txtSaisie As String
    Protected txtMdp As String
    Protected areaSaisie As String
    Protected cmbValeurs As String
    Protected lstSimple As String
    Protected lstMultiple As String
    Protected secret As String
    Protected delimiteur As New Regex("\r\n")

    Private Sub Page_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
        'Die über POST übermittelten Parameter werden abgerufen
        rdMarie = getValue("rdMarie")
        C1 = getValue("C1")
        C2 = getValue("C2")
        C3 = getValue("C3")
        txtSaisie = getValue("txtSaisie")
        txtMdp = getValue("txtMdp")
        areaSaisie = String.Join(",", delimiteur.Split(getValue("areaSaisie")))
        cmbValeurs = getValue("cmbValeurs")
        lstSimple = getValue("lstSimple")
        lstMultiple = getValue("lstMultiple")
        secret = getValue("secret")
    End Sub

    Private Function getValue(ByVal champ As String) As String
        ' ruft den Wert des Feldes [champ] aus der gesendeten Anfrage ab
        ' irgendetwas?
        If Request.Form(champ) Is Nothing Then Return ""
        ' Hier werden der oder die Werte des Feldes abgerufen
        Dim valeurs() As String = Request.Form.GetValues(champ)
        Dim valeur As String = ""
        Dim i As Integer
        For i = 0 To valeurs.Length - 1
            valeur += "[" + valeurs(i) + "]"
        Next
        Return valeur
    End Function

End Class

Die Berechnung der anzuzeigenden Werte erfolgt in der Prozedur [Form_Load]. Der Wert eines „übermittelten“ Feldes wird über die Funktion getValue(C) ermittelt, wobei C der Name des Feldes ist. Die wichtigsten Punkte dieser Funktion sind folgende:

  • Wenn C nicht in der übergebenen Parameterzeichenfolge enthalten ist, wird die leere Zeichenfolge als Wert für C zurückgegeben
  • ansonsten wird das Array der Werte des Feldes C über [Request.Form.GetValues(C)] abgerufen. Diese werden zu einer Zeichenkette in der Form [val1][val2]... verkettet[valn], wobei [vali] der Wert Nr. i des Feldes C ist

Das Feld [areaSaisie] wird auf besondere Weise behandelt. Sein Wert wird vom Browser in der Form areaSaisie=Zeile1\r\nZeile2\r\n... gesendet wobei \r das Codezeichen ASCII 13 (Wagenrücklauf) und \n das Codezeichen ASCII 10 (Zeilenumbruch) ist. Die Funktion getValue(areaSaisie) ist somit die Zeichenkette „Zeile1\r\nZeile2\r\n...“. Diese Zeichenkette wird mit der Methode [Regex.Split] in Zeilen zerlegt. Man erhält dann ein Array von Zeichenketten {Zeile1,Zeile2,...}. Dieses Array wird durch die Methode [String.Join] in die Zeichenkette „Zeile1,Zeile2,...“ umgewandelt. Diese letzte Zeichenkette wird als Wert des Feldes [areaSaisie] angezeigt. Das Ziel war es hier, zu zeigen, wie man die verschiedenen Zeilen eines Feldes HTML vom Typ [TextArea] abrufen kann.

5.4.5. Tests

Wir legen alle Dateien ab (global.asax, global.asax.vb, formulaire.aspx, validation.aspx, validation.aspx.vb) in einen Ordner <application-path>. Wir starten den Cassini-Server mit den Parametern (<application-path>,/mvcform1). Wir erstellen im Ordner <application-path> eine leere Datei mit dem Namen [default.aspx] und rufen anschließend die URL [http://localhost/mvcform1] auf. Da [/mvcform1] der virtuelle Pfad zu einem Ordner und nicht zu einem Dokument ist, zeigt der Webserver das Dokument [default.aspx] an, sofern es vorhanden ist. Aus diesem Grund haben wir dieses Dokument erstellt. Bevor es angezeigt wird, wird das Skript [global.asax] ausgeführt, wodurch schließlich die Seite [formulaire.aspx] angezeigt wird. Deshalb kann die Datei [default.aspx] leer sein.

Nehmen wir an, das validierte Formular sieht wie folgt aus:

Image

Die Verwendung der Schaltfläche [Envoyer] führt zur folgenden Seite:

Image

Beachten wir zunächst die URL der Antwort: [http://localhost/mvcform1/?action=validation]. Dies ist das URL des Attributs [action] des Tags <form> des Formulars [formulaire.aspx]:


        <form name="formulaire" method="post" action="?action=validation">

Sehen wir uns die Werte für die verschiedenen Felder des Formulars nacheinander an:

Feld
Wert
HTML
Kommentare
rdMarie
ja
<input type="radio" value="ja"
name="rdMarie">Ja
<input type="radio" checked
value="nein" name="rdMarie">Nein
Der ermittelte Wert ist das Attribut [value] der markierten Schaltfläche
C1
ein
<input type="checkbox"
value="un" name="C1">1
ebenso
C2
zwei
<input type="checkbox"
checked value="zwei" name="C2">2
dasselbe
C3
 
<input type="checkbox"
value="drei" name="C3">3
Dieses Kontrollkästchen wurde vom Benutzer nicht aktiviert. Sein Wert wurde daher vom Browser nicht übermittelt. Im Code war die Bedingung [Request.Form("C3") is Nothing] somit wahr.
txtSaisie
Programmierung
asp.net
<input type="text"
... name="txtSaisie">
Der resultierende Wert ist der Text, der zum Zeitpunkt der Validierung im Eingabefeld steht
txtMdp
mdp
<input type="password"
...name="txtMdp">
ebenso
areaSaisie
Grundlagen der
Webprogrammierung
<textarea name="areaSaisie">
...</textarea>
ebenso
cmbValeurs
3
<select name="cmbValeurs">
...
<option value="3">Auswahl 3</option>
</select>
Der erhaltene Wert ist das Attribut [value] der ausgewählten Option
lstSimple
3
<select size="3" name="lstSimple">
....
<option value="3">Liste 3</option>
...
</select>
ebenso
lstMultiple
2 4
<select multiple size="3" name="lstMultiple">
...
<option value="2">multiple2
</option>
...
<option value="4">multiple4
</option>
...
</select>
Die erhaltenen Werte entsprechen den Attributen [value] der ausgewählten Optionen
geheim
uneValeur
<input type="hidden"
name="secret" value="einWert">
Der ermittelte Wert ist das Attribut [value] des versteckten Feldes

Wenden wir uns nun den Listen zu. Nehmen wir an, dass der Zustand des Formulars zum Zeitpunkt der Validierung wie folgt ist:

Image

  • Die Option [choix1] ist in der Liste comboBox ausgewählt
  • In den beiden anderen Listen ist keine Option ausgewählt. Um dies zu erreichen, wurden die Schaltflächen [Raz] verwendet.

Hier ist die nach der Bestätigung angezeigte Seite:

Image

Wenn in einer Liste kein Wert ausgewählt ist, sendet der Browser keinen Parameter dafür. Im Code von [validation.aspx.vb] sind die Ausdrücke [Request.Form("lstSimple")] und [Request.Form("lstMultiple")] daher gleich der Konstante [Nothing], woraus sich das oben angezeigte Ergebnis ergibt.

5.5. Den Zustand einer Seite beibehalten

5.5.1. Den Zustand einer Seite mithilfe einer Sitzung beibehalten

Wir kopieren die gesamte vorherige Anwendung in einen neuen Ordner. Wir fügen auf der Seite [validation.aspx] einen Link hinzu, über den der Benutzer zum Formular zurückkehren kann:

Image

Die Änderung, die auf der Seite [validation.aspx] vorgenommen werden muss, ist das Hinzufügen des Links:


.....
            <TR>
                <TD width="84">secret</TD>
                <TD><%=secret%></TD>
            </TR>
        </TABLE>
        <P>
            <a href="?action=formulaire">Retour au formulaire</a>
        </P>
    </body>
</HTML>

Das Attribut [href] des Links hat als Wert eine URL mit einem einzigen Parameter: [action=formulaire]. Dadurch weiß der Server, dass er das Formular so anzeigen muss, wie es zum Zeitpunkt der Validierung aussah. Es besteht also ein Unterschied zur Aktion [init], die ein vordefiniertes Formular anzeigt. Die parametrisierte URL [?action=formulaire] hat eigentlich keine URL. Diese ist daher dieselbe wie die, über die die Validierungsseite angezeigt wurde. Wenn wir uns an die vorherige Untersuchung erinnern, handelt es sich hierbei um die URL des Anwendungsordners. Die Anfrage wird also über den Controller geleitet. Dieser muss nun die Aktion [formulaire] verarbeiten. Der Code von [global.asax.vb] wird wie folgt geändert:


    Sub Application_BeginRequest(ByVal sender As Object, ByVal e As EventArgs)
        ' Die auszuführende Aktion wird abgerufen
        Dim action As String
        If Request.QueryString("action") Is Nothing Then
            action = "init"
        Else
            action = Request.QueryString("action").ToString.ToLower
        End If
        ' die Aktion wird ausgeführt
        Select Case action
            Case "init"
                Server.Transfer("formulaire.aspx", False)
            Case "validation"
                Server.Transfer("validation.aspx", True)
            Case "formulaire"
                Server.Transfer("formulaire.aspx", True)
            Case Else
                Server.Transfer("formulaire.aspx", True)
        End Select
    End Sub

Handelt es sich bei der Aktion um ein „Formular“, wird die Anfrage einfach an die Seite [formulaire.aspx] weitergeleitet. Wir wissen, dass diese Seite ein vordefiniertes Formular anzeigt, das keine variablen Teile enthält. Diese Seite kann das Formular daher nicht mit den Werten anzeigen, die es zum Zeitpunkt der Absendung hatte. Wir möchten diesen Punkt hier verdeutlichen. Wenn sich alle Dateien der Anwendung im Verzeichnis <application-path> befinden, starten wir Cassini mit den Parametern (<application-path>,/mvcform2) und rufen dann die URL [http://localhost/mvcform2] auf. Wir erhalten die folgende Seite (Ausschnitt):

Image

Wir füllen das Formular wie folgt aus und senden es ab:

Image

Wir erhalten die folgende Bestätigungsseite:

Image

Wir verwenden den Link [Retour au formulaire], der auf der obigen Seite vorhanden ist (aber nicht dargestellt wird). Wir erhalten die folgende Antwort vom Server:

Image

Wir stellen fest, dass:

  • die angeforderte URL tatsächlich den Parameter „action=formulaire“ enthält, wie gewünscht
  • das angezeigte Formular die eingegebenen Werte verloren hat.

Wir wissen, warum die eingegebenen Werte nicht mehr vorhanden sind. Wenn wir uns den Code des Dokuments „[formulaire.aspx]“ ansehen, stellen wir fest, dass alles statisch ist und daher jedes Mal dieselbe Seite angezeigt werden muss. Es ist offensichtlich, dass wir diesen Code dynamisch gestalten müssen. Er muss die vom Benutzer validierten Werte anzeigen. Aber wo sollen diese gespeichert werden?

Erinnern wir uns an das eiserne Gesetz des zustandslosen Protokolls HTTP:

  • Die URL [http://localhost/mvcform2] wird angefordert – eine Antwort wird empfangen. Eine Verbindung TCP-IP wurde zu Beginn der Anfrage zwischen dem Client und dem Server hergestellt und am Ende der Antwort beendet.
  • Der Benutzer gibt Daten ein und bestätigt sie. Die URL [http://localhost/mvcform2/?action=validation] wird angefordert – eine Antwort wird empfangen. Eine neue Verbindung TCP-IP wurde zwischen den beiden Partnern geöffnet und anschließend geschlossen.
  • Der Benutzer nutzt den Link [Retour au formulaire]. Die URL [http://localhost/mvcform2/?action=formulaire] wird angefordert – eine Antwort wird empfangen. Eine neue Verbindung TCP-IP wurde erneut zwischen den beiden Partnern geöffnet und anschließend geschlossen.

Die Anfrage-Antwort-Zyklen sind voneinander unabhängig, da jeder von ihnen eine neue Verbindung TCP-IP verwendet. Wenn eine Client-Server-Anwendung eine einzige Verbindung TCP-IP für eine Reihe von Datenaustauschen verwendet, kann der Server einen Client anhand seiner Verbindung identifizieren. Er kann somit Informationen speichern, die er mit einer bestimmten Verbindung verknüpft, und auf diese Weise den Datenaustausch nachverfolgen. Wenn der Datenaustausch über verschiedene Verbindungen erfolgt, kann der Server einen Client nicht anhand einer Verbindung identifizieren. Es bedarf eines anderen Ansatzes. Einen davon haben wir im vorigen Kapitel vorgestellt: den Sitzungsmechanismus. Er ermöglicht es, dass die Anfrage-Antwort-Zyklen Informationen in einem Objekt [Session] speichern, auf das alle nachfolgenden Zyklen zugreifen können.

Da wir nun über eine Anwendung MVC mit Sitzung verfügen, können wir die Datei [global.asax] nicht mehr als Controller verwenden, wie es im vorigen Kapitel gezeigt wurde. Die Rolle des Anwendungscontrollers muss von einer speziellen, dafür vorgesehenen Seite übernommen werden. In diesem Fall ist dies die Seite [main.aspx]. Wir gehen wie folgt vor:

  • Wenn der Benutzer seine Daten bestätigt (Aktion = Validierung), speichert der Controller [main.aspx.vb] diese in der aktuellen Sitzung, bevor er die Validierungsseite anzeigt.
  • Wenn das Formular mit den eingegebenen Werten angezeigt werden soll (Aktion=Formular), ruft der Controller [main.aspx.vb] diese Werte aus der Sitzung ab und übergibt sie an den Kontext, bevor das Formular angezeigt wird.

5.5.2. Der neue Anwendungscontroller

Der Anwendungscontroller besteht aus den beiden Dateien [main.aspx, main.aspx.vb]:

[main.aspx]

<%@ Page src="main.aspx.vb" Language="vb" AutoEventWireup="false" Inherits="main" %>

[main.aspx.vb]


Imports System.Collections.Specialized
Imports Microsoft.VisualBasic

Public Class main
    Inherits System.Web.UI.Page

    Private Sub Page_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
        ' Die auszuführende Aktion wird abgerufen
        Dim action As String
        If Request.QueryString("action") Is Nothing Then
            action = "init"
        Else
            action = Request.QueryString("action").ToString.ToLower
        End If
        ' Die Aktion wird ausgeführt
        Select Case action
            Case "init"
                ' Das vorausgefüllte Formular wird angezeigt
                Context.Items("formulaire") = initForm()
                Server.Transfer("formulaire.aspx", True)
            Case "validation"
                ' Die Bestätigungsseite wird angezeigt, nachdem die übermittelten Werte in der Sitzung gespeichert wurden
                Session.Item("formulaire") = Request.Form
                Server.Transfer("validation.aspx", True)
            Case "formulaire"
                ' Das Formular wird mit den aus der Sitzung übernommenen Werten angezeigt
                Context.Items("formulaire") = Session.Item("formulaire")
                Server.Transfer("formulaire.aspx", True)
            Case Else
                ' Das vorausgefüllte Formular wird angezeigt
                Context.Items("formulaire") = initForm()
                Server.Transfer("formulaire.aspx", True)
        End Select
    End Sub

    Private Function initForm() As NameValueCollection
        ' Das Formular wird initialisiert
        Dim form As New NameValueCollection
        form.Set("rdMarie", "non")
        form.Set("C2", "deux")
        form.Set("txtSaisie", "qqs mots")
        form.Set("txtMdp", "ceciestsecret")
        form.Set("areasaisie", "ligne1" + ControlChars.CrLf + "ligne2" + ControlChars.CrLf)
        form.Set("cmbValeurs", "2")
        form.Set("lstSimple", "1")
        form.Set("lstMultiple", "1")
        form.Add("lstMultiple", "3")
        Return form
    End Function
End Class

Die Struktur des zuvor behandelten Anwendungscontrollers bleibt im Wesentlichen erhalten, mit folgenden Unterschieden:

  • Die Verarbeitung durch den Controller erfolgt in der Prozedur [Form_Load]
  • Im Fall der Aktion [validation] werden die in [Request.Form] vorhandenen Formularwerte in der Sitzung unter dem Schlüssel „Formular“ gespeichert. Anschließend wird die Ausführung an die Seite [validation.aspx] übergeben, die diese Werte anzeigt.
  • Bei allen anderen Aktionen wird die Ausführung in jedem Fall an die Seite [formulaire.aspx] weitergeleitet. Diese erwartet in ihrem Kontext einen Schlüssel „Formular“, der einem Objekt vom Typ [Request.form], c.a.d oder vom Typ [NameValueCollection] zugeordnet ist. Dieses Objekt muss die Sammlung der Werte der Formularfelder enthalten.
  • Falls die Aktion [init] oder eine nicht erkannte Aktion ist, wird die Sammlung der Werte willkürlich von der Funktion [initForm] erstellt.
  • Falls die Aktion [formulaire] ist, handelt es sich bei dieser Sammlung um die Sammlung [Request.Form], die durch die Aktion [validation] in die Sitzung eingefügt wurde

5.5.3. Das neue Formular

Da die Anwendung nicht mehr denselben Inhalt im Formular anzeigt, muss dieses dynamisch generiert werden. Die neue Seite [formulaire.aspx] sieht nun wie folgt aus:


<%@ Page src="formulaire.aspx.vb" Language="vb" AutoEventWireup="false" Inherits="formulaire" %>
<HTML>
    <HEAD>
        <title>Formulaire</title>
        <script language="javascript">
        function effacer(){
            alert("Vous avez cliqué sur le bouton [Effacer]");
        }
        function raz(liste){
            liste.selectedIndex=-1
        }
        </script>
    </HEAD>
    <body>
        <p>
            Gestion d'un formulaire
        </p>
        <hr>
        <form name="formulaire" method="post" action="main.aspx?action=validation">
            <table border="1">
                <tr>
                    <td>
                        Etes-vous marié(e)</td>
                    <td>
                        <p align="center">
                            <INPUT type="radio" value="oui" name="rdMarie" <%=rdouichecked%>>Oui
                         <INPUT type="radio" value="non" name="rdMarie" <%=rdnonchecked%>>Non
                        </p>
                    </td>
                </tr>
                <TR>
                    <TD>Cases à cocher
                    </TD>
                    <TD>
                        <P align="center">
                            <INPUT type="checkbox" value="un" name="C1" <%=c1checked%>>1
                             <INPUT type="checkbox" value="deux" name="C2" <%=c2checked%>>2
                            <INPUT type="checkbox" value="trois" name="C3" <%=c3checked%>>3
                        </P>
                    </TD>
                </TR>
                <TR>
                    <TD>Champ de saisie</TD>
                    <TD>
                        <P align="center">
                            <INPUT type="text" maxLength="30" value="<%=txtSaisie%>" name="txtSaisie">
                        </P>
                    </TD>
                </TR>
                <tr>
                    <td>
                        Mot de passe</td>
                    <td>
                        <p align="center">
                            <input type="password" maxlength="12" size="12" value="<%=txtMdp%>" name="txtMdp">
                        </p>
                    </td>
                </tr>
                <tr>
                    <td>
                        Boîte de saisie</td>
                    <td>
                        <textarea name="areaSaisie"><%=areaSaisie%></textarea>
                    </td>
                </tr>
                <tr>
                    <td>
                        ComboBox</td>
                    <td>
                        <select name="cmbValeurs">
                            <%=cmbValeursOptions%>
                        </select>
                    </td>
                </tr>
                <tr>
                    <td>
                        Liste à choix simple</td>
                    <td>
                        <select size="3" name="lstSimple">
                            <%=lstSimpleOptions%>
                        </select>
                        <INPUT type="button" value="Raz" name="btnRazSimple" onclick="raz(lstSimple)">
                    </td>
                </tr>
                <tr>
                    <td>
                        Liste à choix multiple</td>
                    <td>
                        <select multiple size="3" name="lstMultiple">
                            <%=lstMultipleOptions%>
                        </select>
                        <INPUT type="button" value="Raz" name="btnRazMultiple" onclick="raz(lstMultiple)">
                    </td>
                </tr>
                <tr>
                    <td>
                        Bouton simple</td>
                    <td>
                        <p align="center">
                            <input onclick="effacer()" type="button" value="Effacer" name="btnEffacer">
                        </p>
                    </td>
                </tr>
                <tr>
                    <td>
                        Bouton submit</td>
                    <td>
                        <p align="center">
                            <input type="submit" value="Envoyer" name="btnEnvoyer">
                        </p>
                    </td>
                </tr>
                <tr>
                    <td>
                        Bouton reset</td>
                    <td>
                        <p align="center">
                            <input type="reset" value="Rétablir" name="btnRetablir" runat="server">
                        </p>
                    </td>
                </tr>
            </table>
            <input type="hidden" name="secret" value="uneValeur">
        </form>
    </body>
</HTML>

Erläutern wir die dynamischen Variablen, die im Code HTML vorkommen:

Variable
Rolle
rdouichecked
hat den Wert „checked“, wenn das Optionsfeld [oui] markiert werden soll, andernfalls den Wert „“
rdnonchecked
das Gleiche gilt für das Optionsfeld [non]
c1checked
das Gleiche gilt für das Kontrollkästchen [C1]
c2checked
das Gleiche gilt für das Kontrollkästchen [C2]
c3checked
Das Gleiche gilt für das Kontrollkästchen [C3]
txtSaisie
der Text, der in das Feld [txtSaisie] eingefügt werden soll
txtMdp
der Text, der in das Feld [txtMdp] eingefügt werden soll
areaSaisie
Der Text, der in das Feld [areaSaisie] eingefügt werden soll
cmbValeursOptions
der Text HTML aus den Optionen der Auswahlliste [cmbValeurs]
lstSimpleOptions
der Text HTML der Optionen der Auswahlliste [lstSimple]
lstMultipleOptions
den Text HTML aus den Optionen der Auswahlliste [lstMultiple]
  

Die Werte dieser Variablen werden vom Controller der Seite [formulaire.aspx.vb] berechnet:


Imports Microsoft.VisualBasic
Imports System.Collections.Specialized

Public Class formulaire
    Inherits System.Web.UI.Page

    ' Konstante Felder des Formulars
    Private libellésCmbValeurs() As String = {"choix1", "choix2", "choix3"}
    Private valeursCmbValeurs() As String = {"1", "2", "3"}
    Private libellésLstSimple() As String = {"liste1", "liste2", "liste3"}
    Private valeursLstSimple() As String = {"1", "2", "3"}
    Private libellésLstMultiple() As String = {"multiple1", "multiple2", "multiple3", "multiple4", "multiple5"}
    Private valeursLstMultiple() As String = {"1", "2", "3", "4", "5"}

    ' Dynamische Felder des Formulars
    Protected rdouichecked As String
    Protected rdnonchecked As String
    Protected c1checked As String
    Protected c2checked As String
    Protected c3checked As String
    Protected txtSaisie As String
    Protected txtMdp As String
    Protected areaSaisie As String
    Protected cmbValeursOptions As String
    Protected lstSimpleOptions As String
    Protected lstMultipleOptions As String

    Private Sub Page_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
        ' Die vorherige Anfrage wird aus der Sitzung abgerufen
        Dim form As NameValueCollection
        If Not Context.Items("formulaire") Is Nothing Then
            form = Context.Items("formulaire")
        Else
            form = New NameValueCollection
        End If
        ' Die anzuzeigende Seite wird vorbereitet
        ' Optionsfelder
        rdouichecked = ""
        rdnonchecked = "checked"
        If isEqual(form("rdMarie"), "oui") Then
            rdouichecked = "checked"
            rdnonchecked = ""
        End If
        ' Kontrollkästchen
        c1checked = ""
        If isEqual(form("C1"), "un") Then c1checked = "checked"
        c2checked = ""
        If isEqual(form("C2"), "deux") Then c2checked = "checked"
        c3checked = ""
        If isEqual(form("C3"), "trois") Then c3checked = "checked"
        ' Eingabefelder
        txtSaisie = ""
        If Not form("txtSaisie") Is Nothing Then txtSaisie = form("txtSaisie").ToString
        txtMdp = ""
        If Not form("txtMdp") Is Nothing Then txtMdp = form("txtMdp").ToString
        areaSaisie = ""
        If Not form("areaSaisie") Is Nothing Then areaSaisie = form("areaSaisie").ToString
        ' Listen
        Dim sélections() As String = {}
        If Not form("cmbValeurs") Is Nothing Then sélections = form.GetValues("cmbValeurs")
        cmbValeursOptions = getOptions(valeursCmbValeurs, libellésCmbValeurs, sélections)
        sélections = New String() {}
        If Not form("lstSimple") Is Nothing Then sélections = form.GetValues("lstSimple")
        lstSimpleOptions = getOptions(valeursLstSimple, libellésLstSimple, sélections)
        sélections = New String() {}
        If Not form("lstMultiple") Is Nothing Then sélections = form.GetValues("lstMultiple")
        lstMultipleOptions = getOptions(valeursLstMultiple, libellésLstMultiple, sélections)
    End Sub

    Private Function getOptions(ByRef valeurs() As String, ByRef libelles() As String, ByRef sélections() As String) As String
        ' gibt den Code HTML für die Optionen eines <select>-Tags zurück
        ' Werte: Tabelle der Werte der Tag-Optionen
        ' Bezeichnungen: Tabelle der Bezeichnungen der Optionen des Tags
        ' Auswahlen: auszuwählende Optionen
        Dim iValeur As Integer
        Dim iSelection As Integer
        Dim selected As String
        Dim toString As String = ""
        ' die Liste der Optionswerte wird durchlaufen
        For iValeur = 0 To valeurs.Length - 1
            ' Es wird geprüft, ob der aktuelle Wert ausgewählt werden soll
            selected = "" : iSelection = 0
            Do While iSelection < sélections.Length And selected = ""
                If valeurs(iValeur) = sélections(iSelection) Then selected = "selected"
                iSelection += 1
            Loop
            ' Der Code HTML der Option wird eingefügt
            toString += "<option " + selected + " value='" + valeurs(iValeur) + "'> " _
            + libelles(iValeur) + "</option>" + ControlChars.CrLf
        Next
        ' das Ergebnis wird zurückgegeben
        Return toString
    End Function

    Private Function isEqual(Byval champ As Object, ByVal valeur As String) As Boolean
        ' gibt „wahr“ zurück, wenn das Feld dem Wert entspricht
        If champ Is Nothing OrElse champ.ToString <> valeur Then
            Return false
        Else
            Return true
        End If
    end function
End Class

Wenn die Seite [formulaire.aspx] ausgeführt wird, findet sie in ihrem Kontext einen „Formular“-Schlüssel, der mit der Sammlung der Werte der Felder verknüpft ist, die sie anzeigen soll.


         ' Die vorherige Abfrage wird aus der Sitzung abgerufen
        Dim form As NameValueCollection
        If Not Context.Items("formulaire") Is Nothing Then
            form = Context.Items("formulaire")
        Else
            form = New NameValueCollection
        End If

Man könnte sich fragen, warum überprüft wird, ob [Context.Items("formulaire")] existiert. Tatsächlich weist der Controller diesem Objekt in jedem Fall einen Wert zu. Nichts hindert den Client jedoch daran, die Seite [formulaire.aspx] direkt anzufordern, ohne den Controller zu durchlaufen. In diesem Fall würde der vorstehende Code zwar mit einer leeren Wertesammlung arbeiten, es käme jedoch zu keinem „Absturz“.

Der Code durchläuft die ihm übergebene Wertesammlung, um alle dynamischen Variablen der zugehörigen Seite HTML zu berechnen. Auch wenn er lang ist, ist dieser Code nicht besonders kompliziert, und wir überlassen es dem Leser, sich damit auseinanderzusetzen, um diese Erklärung nicht zu überfrachten. Wir werden uns jedoch näher damit befassen, wie der Code HTML aus den drei Listen vom Typ [select] generiert wird. Dieser Code wird durch die folgende Funktion generiert:

    Private Function getOptions(ByRef valeurs() As String, ByRef libelles() As String, ByRef sélections() As String) As String
         ' gibt den Code HTML der Optionen eines <select>-Tags zurück
         ' Werte: Array der Werte der Tag-Optionen
         ' Bezeichnungen: Array der Bezeichnungen der Tag-Optionen
         ' Auswahlen: auszuwählende Optionen
        Dim iValeur As Integer
        Dim iSelection As Integer
        Dim selected As String
        Dim toString As String = ""
         ' die Liste der Optionswerte wird durchlaufen
        For iValeur = 0 To valeurs.Length - 1
             ' Es wird geprüft, ob der aktuelle Wert ausgewählt werden soll
            selected = "" : iSelection = 0
            Do While iSelection < sélections.Length And selected = ""
                If valeurs(iValeur) = sélections(iSelection) Then selected = "selected"
                iSelection += 1
            Loop
             ' Der Code HTML der Option wird eingefügt
            toString += "<option " + selected + " value='" + valeurs(iValeur) + "'> " _
            + libelles(iValeur) + "</option>" + ControlChars.CrLf
        Next
         ' das Ergebnis wird zurückgegeben
        Return toString
    End Function

Zur Erinnerung: Die Optionen eines <select>-Tags entsprechen dem folgenden Code HTML:

<option [selected] value="...">texte</option>

Für jede Option müssen daher drei Angaben generiert werden:

  • der Wert der Option im Attribut [value]
  • der Text der Option zwischen den Tags <option> und </option>
  • das Schlüsselwort [selected], wenn die Option in der Liste ausgewählt werden soll

Um diese drei Informationen für jede der Optionen zu generieren, erhält die Funktion [getOptions] drei Werte:

  1. das Array der Optionswerte in [valeurs]
  2. das Array der Optionstexte in [libelles]
  3. das Array der auszuwählenden Werte in [sélections]

5.5.4. Die Validierungsseite

Die Validierungsseite bleibt unverändert:

[validation.aspx]


<%@ Page src="validation.aspx.vb" Language="vb" AutoEventWireup="false" Inherits="validation" %>
<HTML>
    <HEAD>
        <title>validation</title>
    </HEAD>
    <body>
        <P>Valeurs saisies</P>
        <HR width="100%" SIZE="1">
        <TABLE id="Table1" cellSpacing="1" cellPadding="1" width="300" border="1">
            <TR>
                <TD width="84">rdMarie</TD>
                <TD><% =rdMarie%></TD>
            </TR>
            <TR>
                <TD width="84">C1</TD>
                <TD><%=C1%></TD>
            </TR>
            <TR>
                <TD width="84">C2</TD>
                <TD><%=C2%></TD>
            </TR>
            <TR>
                <TD width="84">C3</TD>
                <TD><%=C3%></TD>
            </TR>
            <TR>
                <TD width="84">txtSaisie</TD>
                <TD><%=txtSaisie%></TD>
            </TR>
            <TR>
                <TD width="84">txtMdp</TD>
                <TD><%=txtMdp%></TD>
            </TR>
            <TR>
                <TD width="84">areaSaisie</TD>
                <TD><%=areaSaisie%></TD>
            </TR>
            <TR>
                <TD width="84">cmbValeurs</TD>
                <TD><%=cmbValeurs%></TD>
            </TR>
            <TR>
                <TD width="84">lstSimple</TD>
                <TD><%=lstSimple%></TD>
            </TR>
            <TR>
                <TD width="84">lstMultiple</TD>
                <TD><%=lstMultiple%></TD>
            </TR>
            <TR>
                <TD width="84">secret</TD>
                <TD><%=secret%></TD>
            </TR>
        </TABLE>
        <P>
            <a href="main.aspx?action=formulaire">Retour au formulaire</a>
        </P>
    </body>
</HTML>

[validation.aspx.vb]


Imports Microsoft.VisualBasic
Imports System.Text.RegularExpressions

Public Class validation
    Inherits System.Web.UI.Page

    Protected rdMarie As String
    Protected C1 As String
    Protected C2 As String
    Protected C3 As String
    Protected txtSaisie As String
    Protected txtMdp As String
    Protected areaSaisie As String
    Protected cmbValeurs As String
    Protected lstSimple As String
    Protected lstMultiple As String
    Protected secret As String
    Protected delimiteur As New Regex("\r\n")

    Private Sub Page_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
        ' die übermittelten Parameter werden abgerufen
        rdMarie = getValue("rdMarie")
        C1 = getValue("C1")
        C2 = getValue("C2")
        C3 = getValue("C3")
        txtSaisie = getValue("txtSaisie")
        txtMdp = getValue("txtMdp")
        areaSaisie = String.Join(",", delimiteur.Split(getValue("areaSaisie")))
        cmbValeurs = getValue("cmbValeurs")
        lstSimple = getValue("lstSimple")
        lstMultiple = getValue("lstMultiple")
        secret = getValue("secret")
        ' sie werden in der Sitzung gespeichert
        'Session("Formular") = Request.Form
    End Sub

    Private Function getValue(ByVal champ As String) As String
        ' ruft den Wert des Feldes [champ] aus der gesendeten Anfrage ab
        ' Was ist das?
        If Request.Form(champ) Is Nothing Then Return ""
        ' Hier werden der oder die Werte des Feldes abgerufen
        Dim valeurs() As String = Request.Form.GetValues(champ)
        Dim valeur As String = ""
        Dim i As Integer
        For i = 0 To valeurs.Length - 1
            valeur += "[" + valeurs(i) + "]"
        Next
        Return valeur
    End Function
End Class

5.5.5. Die Tests

Die Dateien [main.aspx, main.aspx.vb,formulaire.aspx,formulaire.aspx.vb, validation.aspx, validation.aspx.vb] werden im Verzeichnis <application-path> abgelegt und Casini mit den Parametern (<application-path>,/mvcform3) gestartet. Anschließend rufen wir die URL [http://localhost/mvcform3/main.aspx] auf. Wir erhalten das vorinitialisierte Formular:

Image

Wir füllen das Formular wie folgt aus:

Image

Wir verwenden die Schaltfläche [Envoyer] oben. Wir erhalten die folgende Antwort vom Server:

Image

Wir verwenden den oben genannten Link [Retour au formulaire], um zum Formular zurückzukehren. Wir erhalten folgende neue Antwort:

Image

Das Formular wird tatsächlich so angezeigt, wie wir es abgesendet haben.

5.5.6. Fazit

Das vorangegangene Beispiel hat gezeigt, dass es möglich ist, den Zustand einer Seite über mehrere Anfrage-Antwort-Zyklen zwischen Client und Server hinweg beizubehalten. Allerdings ist dies kein trivialer Vorgang. In einem späteren Kapitel werden wir sehen, dass es mit ASP.NET möglich ist, den Server den Zustand einer Seite selbstständig wiederherstellen zu lassen.