Image
14.10.2015 0 Comments

Aplikácie pre Raspberry Pi 2 s Windows 10 (3. časť)

Ovládanie Raspberry Pi 2 cez internet

V predchádzajúcom PC REVUE sme ukázali jednoduchú aplikáciu Blinky, ktorej cieľom bolo rozblikať LED diódu pripojenú k niektorému portu GPIO dosky Raspberry Pi 2 s operačným systémom Windows 10 IoT Core. Bol to cvičný príklad, ktorý s internetom vecí nemal nič spoločné. Jeho účelom viac než blikanie LED bolo overiť, či je vývojové prostredie správne nakonfigurované, aby bolo možné odladenú aplikáciu preniesť do mikrokontroléra a tam spustiť.

Rasbperry0 ilustračný podklad

Ovládanie cez internet

Aby sa scenár nasadenia mikrokontroléra dal označiť ako súčasť  internetu vecí, treba mať možnosť nejaké zariadenie cez internet ovládať a/alebo z neho cez internet načítať nejaké údaje. Preto cvičnú aplikáciu Blinky zdokonalíme tak, aby bolo možné LED diódu pripojenú k doske ovládať cez webovú stránku. Namiesto LED diódy to môže byť v reálnej aplikácii napríklad hobby či upravené profesionálne zariadenie na nakŕmenie psa, rybičiek, zapnutie zavlažovania a podobne. Aby to bolo možné, na doske musí bežať webový server, prípadne listener, ktorý po zadaní adresy URL dosky vygeneruje stránku HTML s ovládacími prvkami alebo stránku zobrazujúcu údaje získané zo zariadenia pripojeného k mikrokontroléru.

Čo budete potrebovať

Zoznam hardvérových a softvérových  „ingrediencií“ je totožný s lokálnym príkladom Blinky v predošlom čísle. Potrebujete mikrokontrolérovú dosku Raspberry Pi 2 s operačným systémom Windows 10 IoT Core (obraz operačného systému na karte SD vytvoríte podľa návodu na https://ms-iot.github.io/content/en-US/win10/SetupRPI.htm) a LED diódu pripojenú cez obmedzovací odpor 220 ohmov, tak ako je naznačené na schéme. My sme využili výstupný port GPIO 5. 

Pripojenie LED diódy k vhodnému pinu GPIO

Na vývoj aplikácií budete potrebovať Visual Studio 2015, stačí bezplatná verzia Community Edition. Nevyhnutná podmienka v tomto prípade je pripojenie dosky Raspberry Pi 2 k internetu cez eternetový kábel.

Koncepcia riešenia

Príklad pozostáva z dvoch projektov – webového servera, presnejšie listenera , a aplikácie na ovládanie hardvéru, obidva bežia na mikrokontrolérovej doske. Samozrejme, zvládla by to jediná jednoúčelová aplikácia, ale takéto riešenie nie je koncepčné, modulárne ani ľahko rozšíriteľné. V naznačenej konfigurácii môžeme navyše ukázať riešenie dvoch tematických okruhov: ako implementovať webový server a ako možno navzájom komunikovať medzi dvoma aplikáciami v mikrokontrolérovej doske, teda ako implementovať komunikáciu app-to-app.

WebServerApp

Po prístupe na adresu URL webového servera na doske mikrokontroléra vygeneruje  tento server na jednoduchú stránku HTML s ovládacími prvkami typu radio button, pomocou ktorej možno na diaľku prepnúť stav portu.

<html><head><title>Blinky App</title></head>

<body><form action="blinky.html" method="GET">

<input type="radio" name="state" value="on" onclick="this.form.submit()">

On<br><input type="radio" name="state" value="off" checked onclick="this.form.submit()">

Off</form></body></html>

Stránka vygenerovaná webovým serverom na doske Raspberry Pi 2 na ovládanie portu, v tomto prípade na zapnutie

Keďže port ovládajúci LED diódu môže byť v dvoch aktuálnych stavoch, teda v logickej nule a logickej jednotke, má webový server v textových reťazcoch uložené dva varianty kódu HTML stránky. Stránka na obrázku sa zobrazí, ak je port v stave 0, LED dióda nesvieti a čaká sa na zapnutie. Metóda onclick je v tomto prípade implementovaná pre prvok typu radio button s označením On. Ak je port v stave 1 a LED dióda svieti, bude metóda onclick implementovaná pre prvok s označením Off. 

Projekt WebServerApp zaregistruje BackgroundTask. Táto úloha na pozadí umožňuje asynchrónny beh webového servera a zároveň je hostiteľom komunikačnej služby na vzájomnú komunikáciu medzi aplikáciami, ktorú sme nazvali "Ap2AppComService".

BackgroundTaskDeferral _serviceDeferral;

 

public void Run(IBackgroundTaskInstance taskInstance)

{

    _serviceDeferral = taskInstance.GetDeferral();

    var appService = taskInstance.TriggerDetails as AppServiceTriggerDetails;

    if (appService != null && appService.Name == "Ap2AppComService")

    {

        HttpServer server = new HttpServer();

        IAsyncAction asyncAction = Windows.System.Threading.ThreadPool.RunAsync(

        (workItem) =>

        {

            server.StartServer(appService.AppServiceConnection);.

            ...

        });

 

        // listener pre komunikáciu medzi aplikáciami

        appService.AppServiceConnection.RequestReceived += (sender, args) =>

        {

            var message = args.Request.Message;

            ...

        };

    }

}

 

Jadrom webového servera v triede HttpServer je StreamSocketListener, ktorý reaguje na požiadavky z webovej stránky.

public sealed class HttpServer : IDisposable

{

    public HttpServer(int serverPort, AppServiceConnection connection)

    {

      listener = new StreamSocketListener();

      port = serverPort;

      appServiceConnection = connection;

      listener.ConnectionReceived += (s, e) => ProcessRequestAsync(e.Socket);

    }

}

 

V metóde ProcessRequestAsync sa prijmú a spracujú údaje zo socketu a následne je odoslaná odpoveď. Všetko sa realizuje vo forme textových reťazcov, preto aplikácia využíva triedu StringBuilder.

private async void ProcessRequestAsync(StreamSocket socket)

{

    StringBuilder request = new StringBuilder();

    using (IInputStream input = socket.InputStream)

    {

        byte[] data = new byte[BufferSize];

        IBuffer buffer = data.AsBuffer();

        uint dataRead = BufferSize;

        while (dataRead == BufferSize)

        {

            await input.ReadAsync(buffer, BufferSize,

            InputStreamOptions.Partial);

            request.Append(Encoding.UTF8.GetString(data, 0, data.Length));

            dataRead = buffer.Length;

        }

    }

 

    using (IOutputStream output = socket.OutputStream)

    {

        string requestMethod = request.ToString().Split('\n')[0];

        string[] requestParts = requestMethod.Split(' ');

        if (requestParts[0] == "GET")

          await WriteResponseAsync(requestParts[1], output);

    }

}

 

Povely na ovládanie portu sa sprostredkujú cez metódu WriteResponseAsync.

private async Task WriteResponseAsync(string request, IOutputStream os)

{

    string state = "Unspecified";

    bool stateChanged = false;

    if (request.Contains("blinky.html?state=on"))

    {state = "On"; stateChanged = true;}

    else if (request.Contains("blinky.html?state=off"))

    {state = "Off";stateChanged = true;}

    if (stateChanged)

    {

        var updateMessage = new ValueSet();

        updateMessage.Add("State", state);

        var responseStatus = await

        appServiceConnection.SendMessageAsync(updateMessage);

    }

 

    // generovanie html

     using (Stream resp = os.AsStreamForWrite())

     {...}

}

 

V aplikačnom manifeste Package.appxmanifest treba povoliť funkcie potrebné na fungovanie webového servera.

<Capability Name="internetClient" />

<Capability Name="internetClientServer" />

 

Na komunikáciu s inými aplikáciami musíte do manifestu pridať ďalšie rozšírenia, obsahujúce EntryPoint a AppService, kde atribút Name obsahuje názov vašej komunikačnej služby app-to-app.

<Extensions>

    <uap:Extension Category="windows.appService"     

        EntryPoint="WebServerTask.WebServerBGTask">

        <uap:AppService Name="Ap2AppComService" />

    </uap:Extension>

</Extensions>

BlinkyWeb

Aplikácia slúži na ovládanie portu, na ktorom je pripojená LED dióda, prípadne iné zariadenie. Je to veľmi podobný príklad, ako sme ukázali v predošlej časti, jediný rozdiel je v tom, že stav portu je ovládaný cez webový server.  Najskôr treba vytvoriť objekt AppServiceConnection na komunikáciu s inou aplikáciou, v tomto prípade s webovým serverom bežiacim na pozadí, ktorý sprostredkúva povely zadávané používateľom cez webový prehliadač. Pri zostavovaní webového servera si treba niekam uložiť  názov balíčka, konkrétne PackageFamilyName, ktorý je špecifický pre každú aplikáciu. Generuje ho vývojové prostredie Visual Studio a je to kombinácia parametrov Identity.Name z aplikačného manifestu a hash certifikátu aplikácie. Najjednoduchší spôsob, ako tento parameter zistiť, je zostaviť projekt webového servera, zaviesť ho do dosky a zadať príkaz iotstartup list, ktorý vypíše PackageFamilyName aj PackageFullName. Do parametra AppServiceName zadajte reťazec, ktorý ste dali do aplikačného manifestu webového servera:

private async void InitAppSvc()

{

    appServiceConnection = new AppServiceConnection();

    appServiceConnection.PackageFamilyName = "WebServer_nzprx349twr";

    appServiceConnection.AppServiceName = "App2AppComService";

 

    var res = await appServiceConnection.OpenAsync();

    if (res == AppServiceConnectionStatus.Success)

    {

        var message = new ValueSet();

        message.Add("Command", "Initialize");

        var response = await

        appServiceConnection.SendMessageAsync(message);

        appServiceConnection.RequestReceived += OnMessageReceived;

    }

}

V metóde OnMessageReceived sa na základe povelu cez webovú stránku zapína a vypína port ovládajúci LED diódu.

private async void OnMessageReceived(AppServiceConnection sender, AppServiceRequestReceivedEventArgs args)

{

    var message = args.Request.Message;

    string newState = message["State"] as string;

    switch (newState)

    {

        case "On":{await Dispatcher.RunAsync(

                      CoreDispatcherPriority.High,

                     () =>{ZapniLED();});break;}

        case "Off":{await Dispatcher.RunAsync(

                CoreDispatcherPriority.High,

                () =>{TurnOffLED();}); break;}

        case "Unspecified":

        default:break;

    }

}

Keďže ide o tandem dvoch projektov, v článku sú len časti kódu na vysvetlenie fungovania. Kompletné kódy tohto vzorového príkladu nájdete na github.com/ms-iot/samples/tree/develop/App2App%20WebServer.

 

 

 

 

Zobrazit Galériu

Nechajte si posielať prehľad najdôležitejších správ emailom

Mohlo by Vás zaujímať

ITPro

Linux súkromne i pracovne v2.0 (14. časť): Small Business Server

09.11.2016 14:57

Pojem Small Business Server (malý firemný server) začala používať spoločnosť Microsoft ešte v roku 2000 na označenie servera, ktorý ­dokázal plniť úlohy niekoľkých samostatných serverov. Aplikačná vrs ...

ITPro

Industry 4.0: Fikcia alebo už realita?

09.11.2016 14:52

Štvrtá priemyselná revolúcia je pomenovanie rozsiahlych zmien prudko vstupujúcich do súčasného priemyslu. Nositeľom týchto zmien je digitalizácia výroby a optimalizácia všetkých podnikových procesov v ...

ITPro

Vývoj aplikácií UWP pre Xbox One II.

09.11.2016 14:47

V predošlej časti sme ukázali postup, ako si ­vytvoriť vývojársky účet a aktivovať vývojársky režim na hernej konzole Xbox One, aby ste mohli testovať svoje aplikácie. Výhodou hernej konzoly Xbox je v ...

Žiadne komentáre

Vyhľadávanie

Kyocera - prve-zariadenia-formatu-a4-s-vykonom-a3

Najnovšie videá