logi sisse meist KKK

Mõtlesin pisut Ajaxit uurida. Võtsin w3schools.com-i sissejuhatava õpetuse läbi ja hakkasin selle näite baasil asja lähemalt uurima. Nimelt tahtsin Ajaxi päringule saadud vastust enne välja näitamist mudida. Arvasin, et võiks piisata viidatud näite pisukesest täiendusest:

<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" /> 
</head>

<body>
<script type="text/javascript"> 
var vastus;

function parin() {
ajaxFunction();
var loend = vastus.split(":");
document.myForm.time = loend[1];
}

function ajaxFunction() {
    var xmlhttp;
    if (window.XMLHttpRequest) {  // code for IE7+, Firefox, Chrome, Opera, Safari
        xmlhttp=new XMLHttpRequest();
    }
    else {
        // code for IE6, IE5
        xmlhttp=new ActiveXObject("Microsoft.XMLHTTP");
    }

xmlhttp.onreadystatechange=function() {
        if(xmlhttp.readyState==4) {
            vastus=xmlhttp.responseText;
        }
    }
    xmlhttp.open("GET","aeg.php",true);
    xmlhttp.send(null);
}
</script>

<form name="myForm"> 
Name: <input type="text" onkeyup="parin();" name="username" /> 
Time: <input type="text" name="time" /> 
</form>

</body>
</html>

Minu üllatuseks ei oodata järgmise protseduuri käivitamisega, kuniks ajaxFunction() on lõpetanud, vaid proovitakse splittida veel väärtustamata muutujat:

Uncaught TypeError: Cannot call method 'split' of undefined

Miks nii? Kuidas võiks välja näha õige lahendus?

küsitud Nov 29 '09 at 20:46

WK's gravatar image

WK
893712

edited Nov 30 '09 at 16:45

Rene%20Saarsoo's gravatar image

Rene Saarsoo ♦♦
1.1k101121


XMLHttpRequest töötab asünkroonselt, see tähendab, läheb koodi täitmisega edasi ja lehe laadimine töötab edasi eraldi protsessona.

 xmlhttp.open("GET","aeg.php",true);

Kolmas parameeter on "async". Kui see on tõene, töötab päring asünkroonselt. Kui paned "false", siis oodatakse open() vastus ära, enne kui järgmiselt rida minnakse täitma. elik siis:

 xmlhttp.open("GET","aeg.php",false);
link

vastatud Nov 29 '09 at 21:25

Teet's gravatar image

Teet
792410

edited Nov 29 '09 at 21:30

async parameetri abil sünkroonsete päringute tegemine on lihtsama vastupanu teed minek. Et Ajaxiga oma veebilehel tõeliselt rokkida pead siiski valdama ka asünkroonsete päringute tegemise kunsti - sünkroonsete päringute ajal ei saa kasutaja lehel midagi muud teha kui oodata, mis ei pruugi olla meeldiv kui päring peaks kauem aega võtma.

Kirjutasin selle ajaxFunction asemel funktsiooni ajax, mis võtab kaks parameetrit:

  • URL mille poole tahad pöörduda ja
  • Funktsioon, mis kutsutakse välja siis kui päringule saabub vastus.

Vastuse sisu antakse aga edasi selle funktsiooni parameetri kaudu - niiviisi pole sul tarvis seda globaalset vastus muutujat.

function parin() {
    ajax("aeg.php", function(vastus) {
        // käivitatakse peale seda kui serverist vastus käes
        var loend = vastus.split(":");
        document.myForm.time = loend[1];
    });
}

function ajax(url, callback) {
    var xmlhttp = makeXmlHttpRequest();

    // timeout after 30 seconds
    var timeout = setTimeout(function(){
        xmlhttp.abort();
    }, 30*1000);

    xmlhttp.onreadystatechange = function() {
        if (xmlhttp.readyState == 4) {
            clearTimeout(timeout);
            callback(xmlhttp.responseText);
        }
    };
    xmlhttp.open("GET", url);
    xmlhttp.send(null);
}

function makeXmlHttpRequest() {
    if (window.XMLHttpRequest) {
        // code for IE7+, Firefox, Chrome, Opera, Safari
        return new XMLHttpRequest();
    }
    else {
        // code for IE6, IE5
        return new ActiveXObject("Microsoft.XMLHTTP");
    }
}
link

vastatud Nov 30 '09 at 17:07

Rene%20Saarsoo's gravatar image

Rene Saarsoo ♦♦
1.1k101121

edited Dec 01 '09 at 11:13

Aitüma, see lahendus on jätkusuutlikum. Kas on Sul varrukas ka lahendus võimaliku timeoutiga toimetulekuks?

(Nov 30 '09 at 20:03) WK

Täiendasin koodi nõnda, et kui päring võtab üle 30 sekundi, siis see katkestatakse. Aga siin on muidugi veel palju-palju asju, mille osas seda täiendada võiks. Näiteks arvatavasti tahad sa ka kuidagi reageerida sellele kui päringuga midagi untsu läks, mitte lihtsalt see maha vaikida. Seetõttu tuleks reaalses rakenduses kindlasti kasutada mõnda JavaScripti libraryt, kus see kõik on juba kenasti realiseeritud ja läbi testitud. Kui aga tahad ise peensustega lähemalt tutvuda, siis uuri library koodist kuidas seal seda tehakse.

(Dec 01 '09 at 11:20) Rene Saarsoo ♦♦
1

Muide, üpris hea ülevaate sellest asjast paistab andvat http://ajaxpatterns.org/XMLHttpRequest_Call

(Dec 01 '09 at 11:24) Rene Saarsoo ♦♦

Jah, tegelikult vaatangi raamistiku poole. JQueryt uurin, ei ole veel leidnud hääd põhjust midagi muud torkida. Alustuseks proovisin ka lihtsamaid asju ise läbi.

(Dec 01 '09 at 18:29) WK

Muide enamasti on õige lahendus mitte kasutada XMLHttpRequest "käsitsi" vaid võtta mõnda raamistikku a-la MochiKit, JQuery või Prototype.

link

vastatud Nov 30 '09 at 09:27

kt's gravatar image

kt ♦♦
112228

2

Ise olen suur jQuery fänn. Lihtne ja mugav kasutada ning lisaks on üsna paindlik.

(Nov 30 '09 at 13:22) Harri Siirak

jQuery on parim jah, olen YUI-d ka näppinud, jube bloat jQueryga võrreldes, kui soov ainult Ajaxit, DOM-i jms lihtsamaid asju teha.

(Dec 01 '09 at 23:04) Jaanus

XMLHttpRequest object omab atribuuti, mis näitab, kas päring tehakse asünkruunselt (vaikimisi) või sünkroonselt. Sul on vaja sünkroonselt.

googelda "XMLHttpRequest object", saad atribuudi nime teada, ma peast ei julge öelda

link

vastatud Nov 29 '09 at 21:26

peedu's gravatar image

peedu
111

Sinu vastus
lülita eelvaade

Jälgi seda küsimust

By Email:

Pärast sisselogimist saad tellida muudatuse teavitusi siit

By RSS:

Answers

Answers and Comments

Markdown Basics

  • *kaldkiri* või __kaldkiri__
  • **paks kiri** või __paks kiri__
  • link:[tekst](http://url.com/ "pealkiri")
  • pilt?![alt tekst](/path/img.jpg "pealkiri")
  • nummerdatud nimekiri: 1. Foo 2. Bar
  • to add a line break simply add two spaces to where you would like the new line to be.
  • põhilised HTML märgendid on samuti toetatud

Pinu tööpakkumised

kõik pakkumised »

Küsimuse sildid:

×18
×6

küsitud: Nov 29 '09 at 20:46

nähtud: 3,271 korda

viimati uuendatud: Dec 01 '09 at 11:13

Litsents: Creative Commons Attribution License | Kontakt: info@pinu.ee