Avatar billede tipsen Nybegynder
06. maj 2002 - 02:57 Der er 4 kommentarer og
1 løsning

Generaliseret formvalidering

Hej eksperter

Jeg har forskellige formvalidering på mit site - det er bl.a. validering af email, url, navn osv.

På nuværende tidspunkt er det lidt noget slamkode, som jeg gerne vil have generaliseret og smidt ud i en ekstern fil.

Dvs. jeg ønsker at have den essentielle valideringskode i en fil og muligheden for at kalde den med et minimum af kode fra de filer som indeholder formularer.

Mit problem er at jeg ikke helt kan gennemskue en smart måde at splitte koden op på således at jeg både får en generaliseret kode, som jeg kan bruge i forskellige formularer, men samtidig også har en kode der ikke kræver særlig meget for at kunne anvendes fra den fil der indeholder formularen - dvs. koden der bruges til at starte formvalideringen skal ikke være specielt stor!

Jeg leder efter ikke en færdig kode, men ideer og forslag til hvordan jeg opnår ovenstående.

Koden følger her:
<script language="JavaScript">
<!--
//Regular Expressions to check whether email, homepage, name and country are valid
//Garbage values can of course still be submitted but not really ugly garbage values :-)

var emailregexp = /^([A-Z]+)([A-Z0-9_\.\-]*)@([A-Z0-9]+)([.,_,-]([A-Z0-9]+))*\.[A-Z]{2,4}$/i
var homepageregexp = /^((http|https|ftp):\/\/|)(([A-Z0-9][A-Z0-9_-]*)(\.[A-Z0-9][A-Z0-9_-]*)+)\.[A-Z]{2,4}(:(\d+))?(\/)?/i
var nameregexp = /^([a-z])+/i
var countryregexp = /^([a-z])+/i

//================Email Address validation routine=========

function isBlank(s) {
    var len=s.length;
    for(var i=0;i<len;++i) {
        if(s.charAt(i)!= " ") return false
    }
    return true;
}

//Validate fields, submit if OK or generate proper alert message==
function ValidateForm() {

    if (!nameregexp.test(document.forms[0].name.value)) {
        alert("You have to fill in your name!");
        document.forms[0].name.focus();
        return false;
    }

    if (!isBlank(document.forms[0].email.value)) {
        if (!emailregexp.test(document.forms[0].email.value)) {
            errormsg = "\"" + document.forms[0].email.value + "\" is not a valid emailaddress!\n\n";
            errormsg += "It's not necessary to supply an email\nbut if you do, it has to be correct.";
            alert(errormsg);
            document.forms[0].email.focus();
            return false;
        }
    }
    else {
        document.forms[0].email.value = "";
    }

    if (!isBlank(document.forms[0].country.value)) {
        if (!countryregexp.test(document.forms[0].country.value)) {
            errormsg = "\"" + document.forms[0].country.value + "\" is not a valid country!\n\n";
            errormsg += "It's not necessary to supply a country\nbut if you do, it has to be correct.";
            alert(errormsg);
            document.forms[0].country.focus();
            return false;
        }
    }
    else {
        document.forms[0].country.value = "";
    }

    if (!isBlank(document.forms[0].homepage.value)) {
        if (!homepageregexp.test(document.forms[0].homepage.value)) {
            errormsg = "\"" + document.forms[0].homepage.value + "\" is not a valid URL!\n\n";
            errormsg += "It's not necessary to supply a homepage\nbut if you do, it has to be correct.";
            alert(errormsg);
            document.forms[0].homepage.focus();
            return false;
        }
    }
    else {
        document.forms[0].homepage.value = "";
    }

    if (isBlank(document.forms[0].message.value)) {
        alert("You have to type a message!");
        document.forms[0].message.focus();
        return false;
    }
    document.forms[0].submit()
}

//Clear all fields if user cancels the message!
function ClearFields() {
    for (var i=0; i < document.forms[0].elements.length-2; ++i) {
        document.forms[0].elements[i].value = "";
    }
}
//-->
</script>

og kaldes med

onsubmit="return ValidateForm() i formularen.
Avatar billede jakoba Nybegynder
06. maj 2002 - 04:11 #1
Den indlysende er vel at type-klassificere felter. Nogle af de 'tungeste' såsom email, url, real, heltal er veldefineres og kan umiddelbart gemmes i funktioner der så kaldes fra hovedprogrammet. Datoer er nogenlunde nemme hvis de blot får en formatskabelon med.

et fast format for check.funktioner:

function check<typenavn>( formElem [, hjælpeparametre ] ) {
    if ( typespecifik test fail ) {
        generer fejlmelding
        return false
    }
    return true; // OK
}; //end check<typenavn>( Form element objekt [, ?] ) -> boolean


"Generer fejlmelding" skulle så være en struktureret udbygning af fx et array der akkumulerer fejl og tilsidst kan håndteres af formens validerings funktion.

en generel fejlklasse:

function fejlKlasse ( formElem, fejlTekst, auxdata ) {
    this.elem = formElem;  // formelement der fejlede test
    this.tekst = fejlTekst;
    ...
    fejlListe[fejlListe.length] = this; // sæt fejlklassen i kø til samlet handtering.
}; //end fejlklasse

engentlig ingen grund til at check funktionerne returnerer noget.

function check<typenavn>( formElem [, hjælpeparametre ] ) {
    if ( typespecifik test fail ) {
        new fejlKlasse( formElem, "fejlmelding", ??? ); // sætter fejlen i kø
    }
}; //end check<typenavn>( Form element objekt [, ?] )


den overordnede valideringsfunktion ville så blive noget i retning af:

function valider( formObj ) {
    fejlListe = new Array();
    checkEmail( formObj.emalfelt );
    checkUrl( formObj.urlfelt );
    checkDato( formObj.datofelt, "yyyy?mm?dd" );
    if ( formObj.checkbox.checked ) { // lidt skæve bliver der altid :)
        checkDato( formObj.datofelt2, "yyyy?mm?dd" );
    }
    ...
    if ( fejlListe.length == 0 ) {
        return true;    // alles ist gut

    } else {
        fejlListe[0].elem.focus();
        // gic brugeren nogle eller alle fejlmeldinger
        return false;  // nicht gut.
    }
};

Stadig for løst til at implementere, men måske værd at kommentere og modellere på.

mvh JakobA
Avatar billede jakoba Nybegynder
06. maj 2002 - 11:55 #2
Nok det væsentligst der mangler er en god måde at haandtere relationer imellem felternes værdier. hvis formularen fx skal bruges til at købe flybillet skal udrejsedato være senere end submittidspunktet, og hvis der samtidig skal bookes hjemrejsebillet skal hjemrejseksedatoen være senere endnu.

Hvis vi lader check-funktionerne returnere det normaliserede fejltindhold i rette stype skulle det så nogenlunde du:

function checkDato( formElem, format ) {
    ...
    if ( failed ) {
        return false;
    } else {
        return new Date( aar, maaned, dag );
    }

i vadider bliver det så:

    var udDato = checkDato( formObj.datofelt, "yyyy?mm?dd" );
    if ( udDato && udDato.valueOf() < (new Date()).valueOf() ) {
        new fejlKlasse( formObj.datofelt,
"Du kan ikke tage afsted før du køber billetten" );
    if ( formObj.checkbox.checked ) { // lidt skæve bliver der altid :)
        var hjemDato = checkDato( formObj.datofelt2, "yyyy?mm?dd" );
        if ( ( udDato && hjemDato ) & hjemDato.valueOf() < udDato.valueOf() ) {
new fejlKlasse( formObj.datofelt,
"Du kan ikke komme hjem før du tager afsted" );
        }
    }

Det er egentlig ikke så vældig meget der spares :(
Avatar billede jakoba Nybegynder
06. maj 2002 - 16:21 #3
Jeg har lavet en side med dit eksempel efter ovenstående retningslinier:
http://www.jakoba.dk/eksperten/exp207681.html
Avatar billede jakoba Nybegynder
17. maj 2002 - 23:41 #4
Så svare vi også her, men jeg ville heller have noget feedback på hensiger og hvormeget de indfries
Avatar billede tipsen Nybegynder
18. maj 2002 - 00:53 #5
Hej Jakob

Jeg har ikke haft tid til at kigge nærmere på dine forslag, da jeg er i gang med noget eksamenslæsning, men jeg skal nok få klemt det ind på et tidspunkt. Du skal nok få noget respons på dine forslag og hvis jeg laver noget som jeg selv er tilfreds med, vil jeg nok også poste resultatet her!

-I'll be back ;-)
Avatar billede Ny bruger Nybegynder

Din løsning...

Tilladte BB-code-tags: [b]fed[/b] [i]kursiv[/i] [u]understreget[/u] Web- og emailadresser omdannes automatisk til links. Der sættes "nofollow" på alle links.

Loading billede Opret Preview
Kategori
Vi tilbyder markedets bedste kurser inden for webudvikling

Log ind eller opret profil

Hov!

For at kunne deltage på Computerworld Eksperten skal du være logget ind.

Det er heldigvis nemt at oprette en bruger: Det tager to minutter og du kan vælge at bruge enten e-mail, Facebook eller Google som login.

Du kan også logge ind via nedenstående tjenester