Tímto článkem uzavřeme seznámení s technologií Flash Remoting. Především si vyzkoušíme napojení flashové aplikace na webové služby – na příkladu měnového kalkulátoru pracujícího s aktuálními kurzy uvidíme, že jednodušší to už snad být nemůže – a dále nahlédneme do světa databázových aplikací s uživatelským rozhraním ve Flashi.

Volání webových služeb z Flashe

V minulém článku jsme si na prvním příkladu vyzkoušeli volat vlastní službu, kterou jsme vytvořili jako součást serverové strany aplikace. Teď se podíváme na druhé využití technologie Flash Remoting – volání webových služeb poskytovaných jinými servery prostřednictvím protokolu SOAP. Jako ukázku si vytvoříme jednoduchý měnový kalkulátor, který bude při každém výpočtu pracovat s aktuálními měnovými kurzy. Zdrojový kód ukázky si můžete stáhnout a výslednou aplikaci si můžete také vyzkoušet.

Každá webová služba je identifikována adresou souboru WSDL (Web Services Description Language). Tak například můžeme říct, že na adrese http://www.xmethods.net/sd/2001/CurrencyExchangeService.wsdl sídlí webová služba „CurrencyExchangeService“. Ve skutečnosti se na této adrese nachází dokument v jazyce WSDL, který slouží aplikacím jako vstupní brána pro volání této služby. Pokud se na tento dokument podíváme, zjistíme, že popisuje, co příslušná webová služba dělá, jaké poskytuje metody, jaké vstupní parametry tyto metody požadují a v jaké struktuře máme očekávat výsledky. Jazyku WSDL nemusíte rozumět, pokud dostanete od poskytovatele webové služby i její popis v „lidském“ jazyce. V našem případě může znít jednoduše takto: Webová služba, sídlící na výše uvedené adrese, poskytuje jedinou metodu, která se jmenuje getRate, na vstupu požaduje názvy dvou států a na výstupu vrací aktuální směnný kurz mezi měnami těchto států.

Jak tuto službu zavoláme z Flashe? Připomeňme si nejprve úvodní řádky skriptu, které jsou stejné jako v předchozí ukázce:

#include „NetServices.as“
#include „NetDebug.as“
brana = NetServices.createGatewayConnection
  („http://nestor.cz/flashremoting/priklad.php“);

Definovali jsme připojení k bráně aplikačního serveru. Z prvního článku této série víte, že flashová aplikace se nepřipojuje k webovým službám přímo, ale přes aplikační server hostující technologii Flash Remoting. Proto vás nepřekvapí, že adresa je stejná jako v předchozí ukázce.

Dostáváme se k řádku, na kterém si od brány vyžádáme vzdálenou službu. K tomu slouží metoda getService – v minulé ukázce jsme si takto vyžádali službu Astrologie, nyní chceme pracovat s webovou službou a ta je, jak bylo řečeno, identifikována příslušnou adresou souboru WSDL. Příkaz by měl tedy vypadat takto:

currencyExchangeService = brana.getService(
  „http://www.xmethods.net/
    sd/2001/CurrencyExchangeService.wsdl“,
  this
);

Následující příkaz pro vyvolání metody služby by měl vypadat například takto:

currencyExchangeService.getRate(„usa“, „czech republic“);

Proč píšu „by měl“? Protože výše uvedené zatím bohužel platí pouze v případě, že na straně serveru máme k dispozici originální Flash Remoting od firmy Macromedia (tedy ColdFusion nebo řešení pro Javu či .NET). My však pracujeme s produktem AMF PHP a ten v současnosti volání webových služeb ještě nepodporuje. Autoři slibují implementaci v nejbližší době. Nemusíme však na ni čekat, provizorní řešení si velmi snadno vytvoříme už nyní sami a jak uvidíme, na straně Flashe bude potřeba provést jen minimální změny – právě ve způsobu, jakým se odkazujeme na webové služby a jejich metody.

To, co v AMF PHP zatím chybí (podpora volání webových služeb přes SOAP), musíme získat jinde. Zamíříme tedy na stránky projektu NuSOAP a stáhneme si aktuální verzi této knihovny. Jedná se o jediný soubor nusoap.php, který umístíme do kořenového adresáře naší aplikace na serveru. Spojení knihoven NuSOAP a AMF PHP pak provedeme tak, že vytvoříme v naší aplikaci službu, která bude sloužit jako obecná zástupná služba (proxy) pro veškerá volání webových služeb. Tuto obecnou službu nazveme WebServices. V podadresáři sluzby našeho projektu (tam, kde od minula máme skript Astrologie.php) tedy musíme vytvořit skript WebServices.php, který obsahuje následující:

<?
include („nusoap.php“);
class WebServices {
  function WebServices(){
    $this->methodTable = array(
      „callService“ => array(
        „description“ => „Volá webovou službu (SOAP).“,
        „access“ => „remote“,
        „roles“ => „role, list“,
        „arguments“ => array („wsdl“, „metoda“, „parametry“)
      )
    );
  }
  function callService($wsdl, $metoda, $parametry) {
    $soapclient = new soapclient($wsdl, „wsdl“);
    $vysledek = $soapclient->call($metoda, $parametry);
    return $vysledek;
  }
}
?>

Služba WebServices definuje jedinou metodu s názvem callService. Tato metoda má tři parametry: adresu webové služby (WSDL), jméno volané metody této služby a konečně parametry předávané této metodě (jako pole). Jak vidíte, metoda callService neudělá nic víc, než že zavolá klienta SOAP (knihovnu NuSOAP) a to, co obdrží jako výsledek, vrátí sama jako svůj výsledek.

Teď se můžeme vrátit k ActionScriptu, který jsme přerušili v okamžiku, kdy si od brány aplikačního serveru žádáme webovou službu. Výše uvedené dva příkazy tedy musí vypadat takto:

webServices = brana.getService(„WebServices“, this);
webServices.callService(
    „http://www.xmethods.net/
        sd/2001/CurrencyExchangeService.wsdl“,
    „getRate“,
    [„usa“, „czech republic“]
);

Ve finální verzi naší ukázky ovšem vypadá volání webové služby trochu jinak – jako parametry se použijí hodnoty získané z formuláře. Na přijatý výsledek skript zareaguje podobným způsobem, jako v minulé ukázce (je třeba vytvořit metodu callService_Result), proto se tomu již nevěnuji podrobněji, stejně jako zbylým řádkům skriptu, které souvisejí s uživatelským rozhraním.

Webové služby jsou mocným nástrojem, který na svou zlatou éru jistě teprve čeká. Ale už nyní si můžete vyzkoušet složitější a praktičtější příklady než je tento měnový kalkulátor, rozhraní formou webových služeb poskytují Google, Amazon či AltaVista (překlad mezi různými jazyky, ona slavná Babylonská rybka), pomocí webových služeb můžete pracovat i s RSS (RDF Site Summary) či dokonce s protokolem POP3. Je tedy snad už jen otázkou času, než se samozřejmostí freemailových serverů stane flashové rozhraní nerozeznatelné od vašeho Outlooku (či spíše mnohem vtipnější, spojí-li se šikovní programátoři a flashoví „hračičkové“).

Flash Remoting a databáze

Významnou předností technologie Flash Remoting (pro někoho může být hlavním důvodem, proč tímto řešením nahradit starší způsoby komunikace) je velmi snadná tvorba databázových aplikací. Představte si klasickou situaci, kdy chcete do flashové aplikace načíst třeba tabulku nejlepších hráčů. SQL dotaz je otázkou jednoho řádku kódu. Pak ale většinou následuje poměrně pracné „předžvýkání“ získaných dat do takové podoby, kterou Flash dokáže strávit, tedy XML nebo url-encoded. A na straně Flashe je zase nutné data převádět do interních datových struktur (například polí), se kterými lze dále pohodlně pracovat. Flash Remoting vám nabízí nesrovnatelně jednodušší řešení – zavolejte SQL dotaz a jeho výsledek (tedy například v PHP výsledek volání funkce mysql_query) rovnou vraťte jako výstup služby. O vše ostatní se postará Flash Remoting, ve flashové aplikaci si pouze počkáte na naplnění instance speciální třídy RecordSet.

Třídu RecordSet můžeme chápat jako nově zavedený datový typ v ActionScriptu, který ke klasickým typům (String, Array, atd.) přidává datovou strukturu určenou pro ukládání dvourozměrných tabulek, nejčastěji tedy pro výsledky volání databázových dotazů. Třída nabízí množství metod pro běžné operace, jako jsou přístup k jednotlivým záznamům, přidávání, úprava a odstraňování záznamů, třídění nebo filtrování. K datům je dokonce možno přistupovat už během načítání, k dispozici je metoda pro zjištění počtu aktuálně načtených záznamů.

Tím ale nabídka nástrojů pro tvorbu databázových aplikací nekončí. Flash MX přišel s koncepcí komponent uživatelského rozhraní a sám nabídl sadu těch nejobvyklejších. Není tedy příliš velkým překvapením, že Flash Remoting s nimi počítá a umožňuje snadné propojení objektů RecordSet s prvky uživatelského rozhraní, které zobrazují jejich obsah. Potřebujete například naplnit roletku (ComboBox) daty z databáze? Nic snazšího, dohromady to bude na straně Flashe i na straně serveru jen několik řádků kódu. Další nová třída DataGlue (datové lepidlo) umožňuje definovat dokonalejším způsobem, jak se mají data z databáze v tom kterém prvku uživatelského rozhraní zobrazit. A vytvoříte-li si vlastní komponentu, po jejím propojení s objektem RecordSet (respektive obecnější třídou DataProvider) bude komponenta dostávat strukturované informace o všech změnách, které nastanou v datovém zdroji, a bude na ně moci jakkoli reagovat.

Problém s češtinou v AMF PHP

Teď se ještě vraťme k open-source projektu AMF PHP, který nám všechna ta kouzla zpřístupňuje pomocí oblíbeného PHP. Tento projekt je v současnosti stále ve vývoji a jak jsme dnes viděli, v některých oblastech má to podstatné teprve před sebou. Cílem tohoto článku je podpořit váš zájem o Flash Remoting a tím také třeba podnítit zájemce o projekt AMF PHP, aby se do něj aktivně zapojili.

Závažným problémem, na který v současnosti narazí zdejší vývojář, je práce s českým textem, jak jsem naznačil v závěru předchozího článku. Například vytvoříme-li si jednoduchou službu, která vezme přijatý řetězec a v nezměněné podobě nám jej vrátí jako výsledek, dojde k poškození znaků s diakritikou. Přestože jsem na tento problém upozornil autory projektu a v současné době s nimi o něm diskutuji, v aktuální verzi knihovny stále není vyřešen.

Příčinou je konverze řetězců z kódování UTF-8 do ISO-8859-1 (a naopak) po jejich přijetí nebo před jejich odesláním do Flashe. Jelikož UTF-8 je jedinou správnou cestou, jak ve flashových aplikacích zajistit správné zobrazení češtiny na všech platformách a používání tohoto kódování ve všech částech internetové aplikace je podle mě jedinou cestou, jak si zajistit klidný spánek (viz článek Flash MX: Krotíme fonty), doporučuji jednoduše konverzi v rámci knihovny AMF PHP neprovádět a předpokládat UTF-8 jako kódování používané v serverové aplikaci. Pokud se mnou souhlasíte, proveďte si jednoduchou úpravu – v souboru flashservices/io/AMFInputStream.php odstraňte veškerá volání funkce utf8_decode a v souboru flashservices/io/AMFSerializer.php odstraňte veškerá volání funkce utf8_encode. Pak by měl přenos českých řetězců mezi klientem a serverem začít fungovat bez problémů.

Seznámení s technologií Flash Remoting je u konce. Věřím, že tyto články přispěly k tomu, aby se ve Flashi rodilo méně nudných reklam či statických prezentací a více chytrých aplikací.

Starší komentáře ke článku

Pokud máte zájem o starší komentáře k tomuto článku, naleznete je zde.

1 Příspěvěk v diskuzi

  1. Dobrý den,
    potřebuji řešení následující situace. Potřebuji přehrávat SWF animace. Každá trvá jinak dlouho. Potřebuji někam (DB,FILE,..) zaznamenat čas, po který se daná animace přehrávala. Systém běží na linuxu.
    Sháním tedy SWF player, který má nějaké API, event handler nebo tak něco.
    Za radu se finančně odměním. Nevylučuji dlouhodobější spolupráci s daným člověkem. Děkuji mnohokrát.
    Volejte kdykoliv 725 607 670 nebo pište petr.halva@webcorp.cz

Odpovědět