Aktuální vydání

celé číslo

06

2024

MSV 2024

celé číslo

Ajax pro měření a regulaci

Ajax pro měření a regulaci

Petr Klán

Článek popisuje novou techniku v klientském programování zvanou Ajax (zkratka pro asynchronní Java Script a XML). Jde o asynchronní komunikaci mezi klienty a servery. V článku je uvedeno několik typických aplikací, kromě jiných i postup při čtení dat XML z webového procesoru CTRL V4, jehož popis byl uveden v [3]. Výhodou je, že Ajax umožňuje komunikovat ze strany klientu, např. zjistit hodnoty technologických veličin ovládaných webovým serverem. Obecně lze číst jakákoliv data XML kdekoliv v internetu.

1. Úvod

Ajax je zkratka pro asynchronní Java Script a XML. V souvislosti s používáním Ajaxu se hovoří o webu nové generace (web 2.0). O metodě Ajax existuje mnoho knih (viz např. Amazon books s heslem Ajax), webových dokumentů (viz Google s dotazem Ajax filetype: pdf) a také příručka v češtině [1]. S jeho používáním se lze na webu běžně setkat. Například vyhledávač Google pracuje s Ajaxem – viz služba Google Suggest na webové adrese http://www.google.com/webhp?complete=1&hl=en (obr. 1). Název této služby lze do češtiny asi nejlépe přeložit jako „našeptávač Google“. Jestliže se píše dotaz, Google průběžně napovídá jeho možná dokončení. Ajax se používá i v mnoha dalších službách. Ale co to Ajax vlastně je? Ajax je spíše koncept, ne konkrétní programovací metoda nebo její implementace. Je to nová cesta pro tvorbu webových stránek pro interakce se servery.

Obr. 1.

Obr. 1. Google Suggest (našeptávač Google)

Z pohledu měření a regulace předpokládejme, že chceme z webového procesoru z pozice klientu přečíst hodnotu určité technologické veličiny. Pomocí Ajaxu je možné se serveru přímo dotázat, bez synchronizace s další událostí, jako je např. odeslání formuláře.

Ajax je založen na používání objektu nazvaného XMLHttpRequest. Microsoft jej implementoval poprvé v prohlížeči Internet Explorer 5 pro Windows jako součást ActiveX. Mozilla později implementovala XMLHttpRequest jako samostatný objekt v Netscape 7. Apple nyní udělal to samé v Safari 1.2. Opera podporuje objekt XMLHttp-Request počínaje verzí 7.60. Podobně je objekt samostatný (ne součástí ActiveX) ve verzi Internet Explorer 7. Všechny verze Firefox s objektem také pracují.

Smyslem tohoto článku je přiblížit používání objektu XMLHttp-Request. Nejdříve bude objekt, jeho metody a vlastnosti popsány, potom bude uvedeno několik příkladů, jak na používání objektu XMLHttpRequest v konkrétních aplikacích. Jednou z nich bude čtení dat XML z webového procesoru CTRL V4 [3] a příklad jednoduchého parsování těchto dat. Důležité je zjištění, že mnoho aplikací pro měření a regulaci, a to i s požadavkem na práci v reálném čase, se díky Ajaxu může přesunout ze serverových počítačů na klientské. A to je výhodné, neboť klientské počítače jsou zpravidla blíže uživatelům než serverové počítače.

2. Objekt XMLHttpRequest

Podívejme se na objekt XMLHttpRequest podrobněji. Jde o objekt pro komunikaci klientu se serverem. XMLHttpRequest je objekt na straně klientu a musí být před použitím na straně klientu vytvořen v klientském skriptovacím jazyce, např. ve skriptovacím jazyce Java Script. Naštěstí je to jednoduché. Při použití jazyka Java Script:

var xmlHttp;
xmlHttp = new XMLHttpRequest();
if (!xmlHttp)
     alert(„Není mozne otevrit XMLHttpRequest objekt.“);

nebo zjednodušeně pouze

var xmlHttp = new XMLHttpRequest();

První způsob je doplněn oznámením chyby, jestliže prohlížeč z nějakého důvodu objekt nevytvoří. To může být např. tehdy, jde-li o Internet Explorer starší než verze 7. Tam je třeba k vytvoření objektu použít kód

var xmlHttp = new ActiveXObject(„Microsoft.XMLHTTP“);

Kompatibilitu s libovolným typem prohlížeče je možné zajistit několika způsoby. Jednoduchý a přímočarý je např.:

var xmlHttp;
if (window.XMLHttpRequest) { // Normální zpusob
     xmlHttp = new XMLHttpRequest();
} else if (window.ActiveXObject) { // IE starsi nez 7
     xmlHttp = new ActiveXObject(„Microsoft.XMLHTTP“);
}

Nyní, po vytvoření objektu XMLHttpRequest, odkazuje proměnná xmlHttp na tento objekt. Ten má několik vlastností a metod, které jsou souhrnně uvedeny v tab. 1.

Tab. 1. Vlastnosti a metody objektu XMLHttpRequest

Vlastnost

Popis

onreadystatechange

příslušný ovladač událostí

readyState

status: 0 – neinicializovaný, 1 – nahrává se, 2 – nahráno, 3 – interaktivní, 4 – dokončeno

responseText

data ze serveru jsou textový řetězec

responseXML

data DOM jsou kompatibilní s objektem document

status

kód HTTP status (např. 200, 404, 500 apod.)

statusText

textová zpráva spojená s kódem status

Metoda

popis

abort()

ukončí běžnou žádost

getAllResponse-Headers()

vrací všechny hlavičky (jméno a hodnota) jako textový řetězec

getResponseHeader (“<headerName>”)

vrací hodnotu specifikované hlavičky

open(“<method>”, “URL” [, asyncFlag[, “<username> ”[,”<password>”]]])

otevírá spojení a zachycuje odezvu ze specifikované URL adresy; je také možné specifikovat metodu přenosu (get/post), uživatelské jméno a heslo pro chráněné adresy

send(content)

pošle žádost (může obsahovat textový řetězec nebo objekt DOM)

setRequest-Header (“<name>”, “<value>”)

přiřadí hodnotu ke specifikované hlavičce

Podstatou celého Ajaxu je právě používání objektu XMLHttpRequest. To bude ilustrováno na několika příkladech. Všechny dále uvedené příklady používají jazyk Java Script. Příslušné skripty budou vkládány do hlavy dokumentu, tj. budou součástí značky <head>.

3. Čtení obsahu z libovolné webové adresy

První příklad ilustruje, že k získaným datům nemusí být přistupováno jako k dokumentu v HTML, ale spíše jako k jednoduchému toku dat. Kód prvního příkladu je takovýto:

<html>
<head>
<title>Ajax 1</title>
<script>
     var xmlHttp;
     function ziskejURL(url) {
          if (window.XMLHttpRequest) { // IE 7 a ostatni
               xmlHttp = new XMLHttpRequest();
               xmlHttp.onreadystatechange = processStateChange;
               try {
                    xmlHttp.open(„GET“, url, true);
               } catch (e) {
                    alert(e);
               }
               xmlHttp.send(null);
          } else if (window.ActiveXObject) { // IE starsi nez 7
               xmlHttp = new ActiveXObject(„Microsoft.XMLHTTP“);
               if (xmlHttp) {
                    xmlHttp.onreadystatechange = process
                    StateChange;
                    xmlHttp.open(„GET“, url, true);
                    xmlHttp.send();
               }
          }
     }
     function processStateChange() {
          if (xmlHttp.readyState == 4) { // Hotovo
               if (xmlHttp.status == 200) { // Odezva je v poradku
                    document.getElementById(„urlobsah“).inner-
                    HTML = xmlHttp.responseText;
               } else {
                    alert(„Problem: „ + xmlHttp.statusText);
                    }
               }
          }
     </script>
</head>
<body>

<h1>Příklad 1</h1>
Jednoduché získání obsahu URL a jeho zobrazení.<hr>
Tento příklad dovoluje uživateli přistoupit ke specifikované adrese URL a zobrazit její obsah. Příklad ilustruje, že k získaným datům nemusí být přistupováno jako k dokumentu v HTML, ale spíše jako k jednoduchému toku dat. Dokument nemusí být správně interpretován, obrázky mohou chybět apod.
<br><br>
<<b>Je-li třeba prohlížet cizí server, webový prohlížeč to z bezpečnostních důvodů může odepřít. Některé vyhlásí upozornění, některé tento postup přímo nedovolí.
</b>
<br><br>
<form>
<input type=“text“ name=“urlkziskani“ size=“50“
value=“http://ctrlv4.cs.cas.cz/“>
<input type=“button“ value=“Ziskej Obsah URL“ onClick=“ziskejURL(urlkziskani.
value);“>
</form>
<br>
<table border=“1“ bordercolor=“#000000“ cellpadding=“5“ cellspacing=“0“ width=“100%“>
     <tr>
          <td>
               <span id=“urlobsah“>Získaný obsah bude zobrazený zde</span>
          </td>
     </tr>
</table>
<br>
</body>
</html>

Myšlenka prvního příkladu je jednoduchá. Funkce ziskejURL() použije objekt XMLHttpRequest a otevře komunikaci se zadanou adresou URL. Zmiňme se o bloku try…catch pro Internet Explorer 7 a podobné prohlížeče (např. Firefox). Některé prohlížeče nepustí objekt XMLHttpRequest se žádostí o komunikaci na jinou doménu, než odkud jsou webové stránky. Jinými slovy, jestliže se přistupuje k doméně www.cs.cas.cz a zkouší se komunikovat s doménou www.google.com, prohlížeč to nemusí dovolit. Přistoupení k jakémukoliv souboru na doméně www.cs.cas.cz bude zcela bez problémů. Některé prohlížeče takové „křížové skriptování“ tolerují.

Obr. 2.

Obr. 2. Zobrazení souboru index.htm webového procesoru CTRL V4

Důležitým řádkem je xmlHttp.onreadystatechange = processStateChange, který nastavuje ovladače událostí. Když se změní stav žádosti, zavolá se automaticky funkce processStateChange(). Potom je možné dotazovat se na stav objektu XMLHttpRequest a dělat potřebné úkony. V tab. 1 jsou všechny možné hodnoty. Zvláště se využívá případ, kdy je žádost kompletní. Další důležitou věcí je kontrola kódu odezvy HTTP. Jakákoliv jiná hodnota než 200 (HTTP je v pořádku) povede k ohlášení chyby.

Uvedený kód lze jednoduše vyzkoušet: uloží se s příponou .html, následně se otevře webovým prohlížečem a do rámečku se vepíše např. webová adresa. Zmáčkne se tlačítko a získá obsah zadané webové stránky, který však může být značně zjednodušený (bez obrázků, jinak formátovaný apod.). Příklad je na obr. 2 – byl přečten obsah stránky index.htm webového procesoru CTRL V4 (zobrazí se v rámečku) z webové adresy http://ctrlv4.cs.cas.cz/

4. Dynamický našeptávač

Trochu zajímavějším příkladem je dynamický našeptávač. Lze říci, že je to typická aplikace Ajax. Zde je úplný kód:

<html>
<head>
<title>Ajax 2</title>
<script>
     var xmlHttp;
     function ziskejURL() {
               name=encodeURIComponent(document.getElementById(„dotaz“).value);
               url=“prohlizec.php?name=“ + name;
               if (window.XMLHttpRequest) { // IE 7 a ostatni xmlHttp = new XMLHttpRequest();
               xmlHttp.onreadystatechange = processStateChange;
               try {
                    xmlHttp.open(„GET“, url, true);
               } catch (e) {
                    alert(e);
               }
               xmlHttp.send(null);
          } else if (window.ActiveXObject) { // IE starsi nez 7
               xmlHttp = new ActiveXObject(„Microsoft.XMLHTTP“);
               if (xmlHttp) {
                    xmlHttp.onreadystatechange = processStateChange;
                    xmlHttp.open(„GET“, url, true);
                    xmlHttp.send();
               }
          }
     }
     function processStateChange() {
          if (xmlHttp.readyState == 4) { // Hotovo
                    if (xmlHttp.status == 200) { // Odezva v poradku
                    document.getElementById(„naseptavac“).inner-HTML = xmlHttp.responseText;
               } else {
                    alert(„Problem: „ + xmlHttp.statusText);
               }
          }
     }
</script>
</head>
<body>
<h1>Příklad 2</h1>
Dynamický našeptávač.<hr>
Tento příklad ukazuje, jak může být Ajax důležitý jako nápověda. Příkladem je hledání v jednoduché databázi vyhledávačů.
<br><br>
<form>
<input type=“text“ name=“dotaz“ size=“20“ onkeyup=“ziskejURL();“>
</form>
<span id=“naseptavac“></span>
<br>
</body>
</html>

Zde se udělá dotaz v jednoduché databázi vyhledávačů. Do rámečku se postupně napíše dotaz. S každým stiskem klávesy se spustí PHP skript prohlizec.php, obsahující seznam prohlížečů a prohledávací proceduru. Díky asynchronní komunikaci se po stisku každého znaku spouští prohledávání a uživateli je napovídáno, které vyhledávače jsou v databázi a shodují se s právě napsaným dotazem. Příslušný PHP skript je takovýto:

<?php
$databaze = „Seznam | www.seznam.cz | Velice rozsireny;“; //Formovani databaze
$databaze .= „Centrum | www.centrum.cz | Podporovany masivni reklamou;“;
$databaze .= „AlltheWeb | www.alltheweb.com | Nejrychlejsi vyhledavani;“;
$databaze .= „37 | www.37.com | Povazovany za supermetahledac;“;
$databaze .= „AltaVista | www.altavista.com | Velice oblibeny;“;
$databaze .= „Excite | www.excite.com | Obsahly vyhledavac;“;
$databaze .= „Google | www.google.com | Rychle vyhledavani;“;
$databaze .= „HotBot | directory.hotbot.com | Prijemne zpusoby;“;
$databaze .= „Infoseek | infoseek.go.com | Poskytuje kvalitni zdroje;“;
$databaze .= „Looksmart | www.looksmart.com | Chytre vyhledavani;“;
$databaze .= „Opendirectory | dmoz.org | Prijemne ovladani;“;
$databaze .= „Yahoo | www.yahoo.com | Velice rozsireny;“;
$databaze .= „Metacrawler | www.metacrawler.com | Kvalitni metahledac;“;
$dotaz=$_GET[‚name‘]; //Dotaz z HTML
if ($dotaz != NULL)
     {
     $zaznamy=explode(„;“, $databaze); //Deleni databáze do pole
     for ($i=0;$i < count($zaznamy); $i++){ //Prohledani databaze
          $axa=explode(„|“, $zaznamy[$i]);
          if (strstr(strtolower($axa[0]), strtolower($dotaz)))
               echo „<p>$zaznamy[$i]</p>“;
          }
     }
?>

Obr. 3.

Obr. 3. Jednoduchý dynamický našeptávač

Uvedený našeptávač lze vyzkoušet na webové adrese http://www.cs.cas.cz/~pklan/ajax2.html. Při hledání např. prohlížeče z uvedené databáze začínající písmenem „s“ se na zobrazené webové stránce dole objeví nápověda (obr. 3). Tuto aplikaci nelze zkoušet na běžném klientském počítači, jako v předchozím případě, k činnosti je totiž zapotřebí serverový jazyk PHP. Proto je uvedena zmíněná webová adresa, kde lze našeptávač zkoušet. Ještě poznamenejme, že aplikace nerozlišuje malá a velká písmena.

5. Čtení dat v XML z webového procesoru

Třetí příklad ukazuje komunikaci s webovým procesorem CTRL V4 a čtení dat v XML v tomto procesoru. Bude čten soubor temper.xml, který je na webové adrese http://ctrlv4.cs.cas.cz a obsahuje aktuální venkovní teplotu v místě pracoviště autora článku. Odpovídající kód je:

<html>
<head>
<title>Ajax 3</title>
<script>
     var xmlHttp;
     function ziskejURL() {
          url=“http://ctrlv4.cs.cas.cz/temper.xml“;
          if (window.XMLHttpRequest) { // IE 7 a ostatni
               xmlHttp = new XMLHttpRequest();
               xmlHttp.onreadystatechange = processStateChange;
               try {
                    xmlHttp.open(„GET“, url, true);
               } catch (e) {
                    alert(e);
               }
               xmlHttp.send(null);
          } else if (window.ActiveXObject) { // IE starsi nez 7
               xmlHttp = new ActiveXObject(„Microsoft.XMLHTTP“);
               if (xmlHttp) {
                    xmlHttp.onreadystatechange = processState-Change;
                    xmlHttp.open(„GET“, url, true);
                    xmlHttp.send();
               }
          }
     }
     function processStateChange() {
          if (xmlHttp.readyState == 4) { // Hotovo
               if (xmlHttp.status == 200) { // Odezva v poradku
                    xml=xmlHttp.responseText;
                    document.getElementById(„XMLsoubor“).inner-HTML = xml;
                    window.alert(xml);
                    k1=xml.indexOf(„<val>“);
                    k2=xml.indexOf(„</val>“);
                    temperature=xml.substring(k1+5,k2);
                    temp.innerHTML=temperature + „ stupně Celsia“;
               } else {
                    alert(„Problem: „ + xmlHttp.statusText);
               }
          }
     }
</script>
</head>
<body onload=“ziskejURL()“>
<h1>Příklad 3</h1>
Obsah souboru XML z webového miniserveru a jeho zobrazení.<hr>
Tento příklad dovoluje uživateli přistoupit ke specifikovanému serveru a číst soubor XML.
<br><br>
<span id=“XMLsoubor“></span>
<br>
<br>
<br>
Okamžitá teplota v Praze:
<div id=“temp“></div>
</body>
</html>

Soubory XML jsou lokální soubory webového procesoru CTRL V4 [3] určené k přenosu dat. Struktura souboru temper.xml vypadá takto: hodnota val pod značkou te0 nese aktuální teplotu, kterou je nutné přečíst. Ajax zajistí přenos souboru XML do klientu. Tady se jednoduše vyhledá příslušná teplota.

<?xml version=“1.0“ encoding=“ISO-8859-1“ ?>
<data>
     <time>
          <h>@</h>
          <m>@</m>
          <s>@</s>
     </time>
     <te0>
          <id>@</id>
          <val>@</val>
     </te0>
     <te1>
          <id>@</id>
          <val>@</val>
     </te1>
     <te2>
          <id>@</id>
          <val>@</val>
     </te2>
     <te3>
          <id>@</id>
          <val>@</val>
     </te3>
     <te4>
          <id>@</id>
          <val>@</val>
     </te4>
     <te5>
          <id>@</id>
          <val>@</val>
     </te5>
     <te6>
          <id>@</id>
          <val>@</val>
     </te6>
     <te7>
          <id>@</id>
          <val>@</val>
     </te7>
</data>

Obr. 4.

Obr. 4. Zobrazení okamžité teploty z webového procesoru CTRL V4

Na hledání v řetězci je použita standardní vyhledávací procedura indexOf. Teplota je potom zobrazena na webové stránce tak jako na obr. 4. Nahoře je úplný obsah souboru temper.xml a dole je po potvrzení zobrazena okamžitá venkovní teplota. Parsování lze udělat přes standardní objekt DOM nebo ručně, jak naznačuje uvedený příklad. V souboru se vyhledají specifické značky ohraničující hledanou teplotu a hodnota mezi nimi se přečte.

Obr. 5.

6. Závěr

Článek je možné považovat za volné pokračování článku [2] ve smyslu uvádění do nových technik webu a internetu využitelných při měření a regulaci. S jejich použitím lze přecházet k aplikacím na vyšší úrovni. Ajax přenáší některé možnosti ze serverů na klienty. Článek je koncipován jako stručný úvod do této techniky a naznačuje možnosti použití v měření a regulaci v součinnosti s webovým procesorem. Na to může přímo navázat regulační smyčka ovládaná z klientu, v níž bude komunikace s webovým procesorem probíhat periodicky spolu s vysíláním akčních zásahů. Dále jsou k dispozici možnosti vizualizace (viz např. [1]).

Poděkování
Práce byla vytvořena za finanční podpory grantového projektu MŠMT 1N04002.

Literatura:
[1] DARIE, C. a kol.: Ajax a PHP. Zoner Press, 2006.
[2] KLÁN, P.: Získávání informace s použitím webových služeb. Automa, 2005, č. 10, s. 12–16.
[3] KLÁN, P.: Webový procesor pro měření, regulaci a synchronizaci. Automa, 2007, č. 4, s. 58–60.

Petr Klán,
Ústav informatiky AV ČR, v. v. i. a Fakulta strojní ČVUT, Praha,
(pklan@cs.cas.cz)