Formulare vor dem Absenden prüfen
Vorzugsweise werden die Felder eines Formulars direkt bei der Eingabe von einem Javascript geprüft.
- submit fängt das Absenden des Formulars ab.
- blur fängt die Eingabe bei input type="text" ab.
- change fängt eine Änderung in select-Listen ab und erkennt das Ändern in textarea.
- click fängt das Ändern bei input type="radio" und type="checkbox" ab (onchange funktioniert heute auch zuverlässig bei Checkboxen).
Die Validierung mit Javascript erspart das Prüfen durch die serverseitige Anwendung nicht: Der Benutzer könnte Javascript deaktivert haben (auch wenn echte Benutzer Javascript nur noch selten ausschalten: Für Hacker und Spammer ist das Umgehen der Javascript-Validierung ein Klacks).
Absenden von Formularen verhindern
Um zu verhindern, dass der Browser die Formulardaten beim Klick auf den Submit-Button des Formulars direkt an den Server leitet, fängt das Script das Absenden der Eingaben mit einem EventListener auf dem submit-Event ab.
HTML
<form id="myform" action="formhandler.php"
method="post">
…
</form>
----------------------------------------------------------------------------
SCRIPT
const myform = document.getElementById('myform');
myform.addEventListener('submit',function (evt) {
let error = false;
…
if (error) {
evt.preventDefault();
}
});
preventDefault verhindert die vorgegebene Aktion des Browsers – das Übermitteln der Formulardaten an die Anwendung auf dem Server. Für IE8 und älter wird das Absenden des Formulars durch evt.returnValue = false unterdrückt.
Weil preventDefault das auslösende Event braucht, kann das Event immer als Parameter des Event Handlers (evt) eingesetzt werden.
Am Rande: Für IE8 war die Funktion noch elem.attachEvent ('onsubmit',formHandler);
blur – Fehleingaben in Formularen sofort abfangen
onblur erkennt Fehleingaben in dem Moment, in dem die Maus oder der Finger das Eingabefeld verlässt. Das klärt den Benutzer schneller über fehlende oder falsche Eingaben auf als Fehlermeldungen, die erst beim submit erscheinen.
Das Prüfen von Formulareingaben ist immer eine langatmige Angelegenheit. Damit das Script übersichtlich bleibt: Eingaben mit try … catch (e) … throw testen.
input type="text": elem.value
Der Wert eines Eingabefelds mit type="text" kann direkt über das value-Attribut des input-Tags abgefragt werden.
<label> <span>Name</span> <input type="text" name="formname" value="" placeholder="Name (erforderlich)" required> </label>
let errorname = true; let formname = document.getElementsByName('formname')[0]; formname.onfocus = function () { this.setAttribute('style','background: white'); } formname.onblur = function () { if (this.value.match(regexName)) { this.setAttribute('style','background: white'); document.querySelector('.msg.formname').innerHTML = ''; document.querySelector('.msg.formname').setAttribute('style','display:none'); errorname = false; } else { this.setAttribute('style','background:seashell'); document.querySelector('.msg.formname').innerHTML = 'Bitte geben Sie ihren Namen ein!'; document.querySelector('.msg.formname').setAttribute('style','display:block'); errorname = true; } }
Der reguläre Ausdruck regexName prüft die Zeichenketten vor der Übermittlung anhand einer Whitelist.
Eine Whitelist für Namen erlaubt z.B. Buchstaben von A bis Z und Umlaute bzw. Sonderzeichen der Sprache wie ä, ö, é. Dazu kommen Leerzeichen, Bindestriche, Punkte und Apostroph, damit auch È. D'Artagnan-Hörbrügger als Name anerkannt wird. Durch die Whitelist bleiben gefährliche Sonderzeichen wie <, >, % und : außen vor.
Namen /^([ \u00c0-\u01ffa-zA-Z\.' \-]{3,})+$/; Telefonnummern /^([0-9\.-\/ ()]{7,})$/; Email /^([a-z0-9_\.-]+)@([\da-z\.-]+)\.([a-z\.]{2,6})$/ URL /^(https?:\/\/)?([\da-z\.-]+)\.([a-z\.]{2,6})([\/\w \.-]*)*\/?$/
Formular-Eingaben testen mit Regulären Ausdrücken.
\u00c0-\u01ffa erlaubt die diakritischen Sonderzeichen wie Umlaute, Zirkumflex, Gravis und Tilde der Sprachen im Namen von Eingabefeldern.
Das wird der Anwendung auf dem Server natürlich die erneute Prüfung nicht ersparen, aber dem Benutzer u.U. das Hin- und Her zwischen Browser und Server.
Werte von select – option Listen auslesen
Bei Select-Listen ist der Rückgabewert nicht der Text des option-Tags, sondern der Wert des value-Attributs. Wenn kein value-Attribut im option-Tag eingetragen ist, liefert elem.value den Text zwischen öffnenden und schließenden option-Tags.
Die Javascript-Validierung interessiert aber im Grunde genommen nur dafür, ob der Benutzer ein Element ausgewählt hat oder das Feld ausgelassen hat.
<label><span>Buchtitel</span> <select name="fieldtitel"> <option>–– Buchtitel wählen ––</option> <option value="n417">Eine Geschichte von fast allem</option> <option value="n418">Das Heideprinzesschen</option> <option value="n419">Lecture Notes on Physics</option> </select> </label>
const formtitel = document.getElementsByName('formtitel')[0]; formtitel.onchange = function () { if (formtitel.selectedIndex == 0) { this.setAttribute('style','background:seashell'); document.querySelector('.msg.formtitel').innerHTML = 'Bitte wählen Sie den Buchtitel!'; document.querySelector('.msg.formtitel').setAttribute('style','display:block'); errortitel = true; } else { this.setAttribute('style','background: white'); document.querySelector('.msg.formtitel').innerHTML = ''; document.querySelector('.msg.formtitel').setAttribute('style','display:none'); errortitel = false; } }
Bleibt es beim Eintrag »Buchtitel wählen« auf dem Index 0, gibt es einen Hinweis und das error-Flag wird gesetzt.
Werte von type="radio" auslesen
onchange feuert nicht, wenn ein Radio-Button aktiviert oder deaktiviert wird. Für jedes Eingabefeld einer Radio-Gruppe muss einzeln beim click-Event geprüft werden, ob es selektiert wurde.
Zusammengehörige radio-Buttons haben ein gemeinsames name-Attribut, über das Javascript alle input-Elemente einer Radio-Gruppe als Array anspricht.
<input type="radio" name="fieldbooktype" value="Gebunden" /> Gebundene Ausgabe <input type="radio" name="fieldbooktype" value="Taschenbuch" /> Taschenbuch <input type="radio" name="fieldbooktype" value="eBook" checked /> eBook
const fieldbooktype = document.querySelector('input[name="fieldbooktype"]:checked');
Werte von type="checkbox" auslesen
Eingabefelder type="checkbox" bilden zwar genauso wie Radio-Buttons eine Gruppe, aber bei Checkboxen kann mehr als ein Feld aktiviert sein.
querySelectorAll ist eine riesige Erleichterung, denn dank querySelectorAll das Script holt mit einer Anweisung alle aktivierten Checkboxen in eine NodeList.
<input type="checkbox" name="fieldpack" value="box1"> Geschenkbox Blau <input type="checkbox" name="fieldpack" value="box2"> Schleife <input type="checkbox" name="fieldpack" value="box3"> Lesezeichen
const fieldpack = document.querySelectorAll( 'input[name="fieldpack"]:checked' );
Mit querySelectorAll erreicht Javascript die Felder des Formulars anhand von CSS-Attribut-Selektoren.
Formulare über mehrere Seiten
HTML-Seiten vergessen einen Besucher – und auch die Daten aus Formularen – sofort, wenn die Seite verlassen wird. Da helfen nur Cookies und Sessions, die Daten von einer Seite auf die nächste Seite zu übernehmen.
Formular absenden ohne Javascript?
Hacker und Spammer verwenden nicht die neusten Versionen der Browser, sondern lieber die ganz alten Schätzchen. Damit sie nicht durch die Fehlermeldungen von Javascript blockiert werden, schalten sie Javascript ab.
Als Gegenmaßnahme kann das Formular prüfen, ob Javascript überhaupt aktiviert ist und ein Absenden ohne Javascript von vornherein unterbinden.