Bevezetés az Akka HTTP-be

1. Áttekintés

Ebben az oktatóanyagban az Akka Actor & Stream modelljeinek segítségével megtudhatjuk, hogyan kell beállítani az Akkát olyan HTTP API létrehozására, amely biztosítja az alapvető CRUD műveleteket.

2. Maven-függőségek

Először vessünk egy pillantást az Akka HTTP használatához szükséges függőségekre:

 com.typesafe.akka akka-http_2.12 10.0.11 com.typesafe.akka akka-stream_2.12 2.5.11 com.typesafe.akka akka-http-jackson_2.12 10.0.11 com.typesafe.akka akka-http- testkit_2.12 10.0.11 teszt 

Természetesen megtalálhatjuk ezen Akka könyvtárak legújabb verzióját a Maven Central-on.

3. Színész létrehozása

Példaként létrehozunk egy HTTP API-t, amely lehetővé teszi a felhasználói erőforrások kezelését. Az API két műveletet támogat:

  • új felhasználó létrehozása
  • meglévő felhasználó betöltése

Mielőtt HTTP API-t tudnánk biztosítani, olyan szereplőt kell létrehoznunk, amely biztosítja a szükséges műveleteket:

class UserActor kiterjeszti az AbstractActor {private UserService userService = new UserService (); statikus kellékek kellékei () {return kellékek létrehozása (UserActor.class); } @ Nyilvános felülbírálása Fogadja a createReceive () {return ReceiveBuilder () .match (CreateUserMessage.class, handleCreateUser ()) .match (GetUserMessage.class, handleGetUser ()) .build (); } privát FI.UnitApply handleCreateUser () {return createUserMessage -> {userService.createUser (createUserMessage.getUser ()); sender () .tell (új ActionPerformed (String.format ("% s felhasználó létrehozva.", createUserMessage.getUser (). getName ())), getSelf ()); }; } private FI.UnitApply handleGetUser () {return getUserMessage -> {sender (). tell (userService.getUser (getUserMessage.getUserId ()), getSelf ()); }; }}

Alapvetően kiterjesztjük a AbstractActor osztály és annak megvalósítása createReceive () módszer.

Belül createReceive (), mi vagyunk bejövő üzenettípusok feltérképezése a megfelelő típusú üzeneteket kezelő módszerekre.

Az üzenettípusok egyszerű, sorosítható tárolóosztályok, néhány mezővel, amelyek leírnak egy bizonyos műveletet. GetUserMessage és egyetlen mezője van Felhasználói azonosító a betöltendő felhasználó azonosítására. CreateUserMessage tartalmaz egy Felhasználó objektum a felhasználói adatokkal, új felhasználót kell létrehoznunk.

Később meglátjuk, hogyan lehet a bejövő HTTP kéréseket lefordítani ezekbe az üzenetekbe.

Végül az összes üzenetet átruházzuk a UserService példány, amely biztosítja a tartós felhasználói objektumok kezeléséhez szükséges üzleti logikát.

Ezenkívül vegye figyelembe a kellékek () módszer. Amíg a kellékek () módszer nem szükséges a kiterjesztéshez AbstractActor, később hasznos lesz a ActorSystem.

A színészekről folytatott alaposabb beszélgetéshez tekintse meg az Akka Actors bemutatkozását.

4. HTTP útvonalak meghatározása

Van egy színész, aki a tényleges munkát végzi helyettünk, csak annyi dolgunk van, hogy biztosítsunk egy HTTP API-t, amely a bejövő HTTP kéréseket delegálja színészünknek.

Akka az útvonalak fogalmával írja le a HTTP API-t. Minden művelethez szükségünk van egy útvonalra.

HTTP szerver létrehozásához kibővítjük a keretrendszert HttpApp és végrehajtja a útvonalak módszer:

class UserServer kiterjeszti a HttpApp {private final ActorRef userActor; Timeout timeout = új időtúllépés (Duration.create (5, TimeUnit.SECONDS)); UserServer (ActorRef userActor) {this.userActor = userActor; } @Orride public Route Routes () {return path ("users", this :: postUser) .orElse (path (segment ("users"). Slash (longSegment ()), id -> route (getUser (id)) )); } privát útvonal getUser (hosszú azonosító) {return get (() -> {CompletionStage user = PatternsCS.ask (userActor, új GetUserMessage (id), timeout) .thenApply (obj -> (Opcionális) obj); return onSuccess (() -> felhasználó, végrehajtva -> {if (perform.isPresent ()) visszatér teljes (StatusCodes.OK, perform.get (), Jackson.marshaller ()); else return complete (StatusCodes.NOT_FOUND); }); }); } private Route postUser () {return route (post (() -> entitás (Jackson.unmarshaller (User.class), felhasználó -> {CompletionStage userCreated = PatternsCS.ask (userActor, new CreateUserMessage (user), timeout) .theApply (obj -> (ActionPerformed) obj); return onSuccess (() -> userCreated, perform -> {return complete (StatusCodes.CREATED, perform, Jackson.marshaller ());});}))); }} 

Most elég sok kazán van itt, de vegye figyelembe, hogy ugyanazt a mintát követjük, mint korábban térképészeti műveletek, ezúttal útvonalakként. Bontjuk le egy kicsit.

Belül getUser (), egyszerűen beburkoljuk a bejövő felhasználói azonosítót egy típusú üzenetbe GetUserMessage és továbbítsuk ezt az üzenetet a mi userActor.

Miután a színész feldolgozta az üzenetet, a onSuccess kezelőt hívnak, amelyben mi teljes a HTTP kérést egy válasz küldésével, amely egy bizonyos HTTP állapotot és egy bizonyos JSON törzset tartalmaz. A Jackson rendező segítségével a színész által adott választ JSON karakterláncba soroljuk.

Belül postUser (), kicsit másképp csináljuk a dolgokat, mivel JSON-testet várunk a HTTP-kérésben. Használjuk a entitás () módszer a bejövő JSON törzs egy a Felhasználó tárgy, mielőtt a CreateUserMessage és továbbadjuk színészünknek. Ismét Jackson segítségével térképezzük fel a Java és a JSON-t, és fordítva.

Mivel HttpApp elvárja tőlünk, hogy egyetlen anyagot adjunk Útvonal objektummal kombináljuk mindkét útvonalat egyetlen útvonalra a útvonalak módszer. Itt használjuk a pálya irányelv, hogy végül megadja azt az URL-utat, amelyen az API-nknak elérhetőnek kell lennie.

Kötjük az általunk biztosított útvonalat postUser () az ösvényre / felhasználók. Ha a bejövő kérés nem POST kérés, az Akka automatikusan belép a különben elágazik, és elvárja az utat / felhasználók / és a HTTP metódus legyen GET.

Ha a HTTP módszer GET, akkor a kérést továbbítja a getUser () útvonal. Ha a felhasználó nem létezik, az Akka visszaadja a 404 HTTP-állapotot (Nem található). Ha a módszer nem POST vagy GET, akkor az Akka a 405 HTTP-státuszt adja vissza (a módszer nem engedélyezett).

Ha további információt szeretne kapni a HTTP útvonalak Akkával történő megadásáról, tekintse meg az Akka dokumentumokat.

5. A szerver indítása

Miután létrehoztunk egy HttpApp a fentiekhez hasonlóan néhány sornyi kóddal indíthatjuk el a HTTP szerverünket:

public static void main (String [] args) dobja a {ActorSystem system = ActorSystem.create ("userServer") kivételt; ActorRef userActor = system.actorOf (UserActor.props (), "userActor"); UserServer server = új UserServer (userActor); server.startServer ("localhost", 8080, rendszer); }

Egyszerűen létrehozunk egy ActorSystem típusú egyetlen színésszel UserActor és indítsa el a szervert helyi kiszolgáló.

6. Következtetés

Ebben a cikkben megismertük az Akka HTTP alapjait egy példával, amely bemutatja, hogyan állíthat be HTTP-kiszolgálót, és hogyan teheti ki a végpontokat erőforrások létrehozása és betöltése érdekében, hasonlóan a REST API-hoz.

Szokás szerint az itt bemutatott forráskód megtalálható a GitHubon.