Kako sestaviti vtično Golang aplikacijo in izkoristiti AWS Lambda Layers.

Golang - zakaj je vredna vaše pozornosti?

Golang je odprtokodni programski jezik, ki ga je zasnoval in izvajal Google. Zelo pogosto se uporablja v sodobnih aplikacijah, zlasti v oblaku. Najbolj značilne lastnosti so:

  • Golang je statično vtipkan - omogoča manjšo prilagodljivost, a vas ščiti pred napakami,
  • Objektno ni. Vendar lahko ustvarite strukture in vmesnike, kar vam daje 3 od 4 načel OOP: odvzem podatkov, kapsulacija in polimorfizem. Dedovanje je edino manjkalo,
  • Goroutine! - največja izvedba svetlobnih niti, kar sem jih kdaj uporabil. Omogoča vam, da ustvarite novo nit na zelo enostaven način s pomočjo go-operatorja in komunicirate med različnimi potekami z uporabo kanalov,
  • Sestavlja se v enotno binarno datoteko z vsemi odvisnostmi - ni več konfliktov paketov!

Osebno menim, da je Golang največji jezik, ki ga uporabljam vsakodnevno. Vendar pa ta članek ne bo o ustvarjanju svoje prve funkcije ali tiskanju "Hello World". Pokazal vam bom malo bolj napredne stvari. Če ste začetnik in želite izvedeti več o Golangu, obiščite njegovo glavno stran.

AWS Lambda & Golang

AWS Lambda je ena najbolj priljubljenih računalniških storitev brez strežnika v javnem oblaku, ki jo je novembra 2014 izdal Amazon Web Services. Omogoča vam zagon kode kot odziv na dogodke, kot so sprožilci DynamoDB, SNS ali HTTP, ne da bi zagotovili ali upravljali strežnike! Veste, kaj je v resnici super? Od januarja 2018 podpira čas izvajanja Golang. Delo z AWS Lambda je res preprosto - preprosto naložite zip paket s kodo in vsemi odvisnostmi (en binarni zapis pri uporabi Golang).

Hitro naprej, 4 leta kasneje v letu 2018 re: Invent AWS izdaja Lambda Sloje, ki omogoča shranjevanje in upravljanje podatkov, ki se delijo med različnimi funkcijami, v enega ali celo več računov AWS! Na primer, medtem ko uporabljate Python, lahko vse odvisnosti postavite v dodaten sloj, ki ga bodo kasneje lahko uporabili tudi drugi Lambdasi. V vsakega paketa z zadrgo ni treba več postavljati različnih odvisnosti! V svetu Golang je situacija drugačna, saj AWS Lambda od vas zahteva, da naložite sestavljeno binarno datoteko. Kako lahko koristimo od AWS Lambda Slojev? Odgovor je preprost - sestavite modularno aplikacijo z uporabo vtičnikov Golang!

Golang Plugins - način za izdelavo modularne aplikacije

Golang Plugins je funkcija, izdana v Go1.8, ki omogoča dinamično nalaganje knjižnic v skupni rabi (.so datotek). Omogoča vam, da nekaj kode izvozite v ločeno knjižnico ali uporabite vtičnik, ki ga je pripravil in sestavil nekdo drug. Obljublja pa, da obstaja nekaj omejitev:

  • Vaš vtičnik mora biti en sam glavni modul,
  • Naložite lahko samo funkcije in spremenljivke, ki se izvozijo kot simboli ELF,
  • Zaradi statičnega tipkanja morate vsak naloženi simbol vstaviti v pravilno vrsto. V najslabšem scenariju morate v kodi določiti pravi vmesnik,
  • Deluje samo za Linux in MacOS. Osebno tega ne štejem kot slabost :)

Izdelava in preizkušanje vašega prvega vtičnika

Zdaj ustvarimo svoj prvi vtičnik. Kot primer bomo ustvarili preprost modul za šifriranje niza. Vrnimo se k osnovam in implementiramo 2 preprosta algoritma za šifriranje - Ceasar in Verman.

  • Cezarjev šifrant je algoritem, ki ga je prvi uporabil Julius Ceases. Vsako črko v besedilu premakne za določeno število mest. Če želite na primer šifrirati besedo golang s tipko 4, boste dobili ktpek. Dešifriranje deluje na enak način. Črke morate le prestaviti v nasprotno smer.
  • Verman šifra je podobna Ceaserju, temelji pa na isti premikajoči se ideji, razlika je v tem, da vsako črko premaknete po različnem številu položajev. Za dešifriranje besedila morate imeti ključ, ki vsebuje položaje, ki se uporabljajo za šifriranje besedila. Če želite na primer šifrirati besedo golang s tipko [-1, 4, 7, 20, 4, -2], boste dobili prihodnost.

Celotna izvedba tega primera je na voljo tukaj.

Izvedba vtičnikov

Naslednji delček vsebuje izvajanje obeh zgoraj omenjenih algoritmov. Za vsako izvedemo 2 načina šifriranja in dešifriranja našega besedila:

Kot vidite, smo izvozili sem 3 različne simbole (Golang izvozi samo te identifikatorje, ki se začnejo z zgornjo črko):

  • EncryptCeasar - niz funkc (int, string), ki šifrira besedilo z algoritmom Ceasar,
  • DecryptCeaser - niz funkc (int, string), ki dešifrira besedilo z algoritmom Caeser,
  • VermanCipher - spremenljivka tipa vermanCipher, ki izvaja 2 metoda: šifriranje: string func (string) in dešifriranje: func () (* niz, napaka)

Če želite sestaviti ta vtičnik, morate zagnati naslednji ukaz:

pojdite build -buildmode = plugin -o plugin / cipher.so plugin / cipher.go

Za zdaj ni nič posebnega - ustvarjenih je bilo nekaj preprostih funkcij in modul je bil sestavljen kot vtičnik z dodajanjem argumenta -buildmode = plugin.

Naložite in preizkusite vtičnik

Zabava se začne, ko želimo v svoji aplikaciji uporabiti sestavljeni vtičnik. Ustvarimo preprost primer:

Najprej morate uvoziti paket vtičnikov golang. Vsebuje samo dve funkciji - prva je za nalaganje knjižnice v skupni rabi, druga pa za iskanje izvoženega simbola. Za nalaganje knjižnice morate uporabiti odprto funkcijo, ki zahteva pot do vašega skupnega vtičnika in vrne spremenljivko tipa Plugin. Če nalaganje knjižnice ni mogoče (npr. Napačna pot ali poškodovana datoteka), ta funkcija vrne napako, ki jo je treba obravnavati.

Naslednji korak je nalaganje vsakega izvoženega simbola z uporabo metode Lookup. Majhna nevšečnost je, da morate vsako izvoženo funkcijo naložiti posebej. Vendar lahko več funkcij združite skupaj na enak način, kot je bilo to storjeno za simbol VermanCipher. Ko naložite vse simbole, ki jih želite uporabiti, jih morate vstaviti v pravilno vrsto. Golang je statično vtipkan jezik, tako da ni drugih načinov uporabe teh simbolov brez vstavljanja. Ne pozabite, da ko izvozite spremenljivko, ki izvaja nekaj metod, jo morate vstaviti v pravilno vrsto vmesnika (za obdelavo tega sem moral definirati vmesnik encryptionEngine). \ Newline \ newline

Za sestavljanje in zagon aplikacije uporabite naslednji ukaz:

pojdite sestaviti app.go
./app

V izhodu bi morali videti šifrirano in dešifrirano besedilo kot dokaz, da algoritem deluje pravilno.

Uporabite vtičnik v AWS lambda

Za uporabo našega vtičnika v AWS Lambda moramo v naši aplikaciji narediti nekaj sprememb:

  • AWS Lambda pritrdi plasti v imenik / opt v lambda vsebniku, zato moramo vtičnik vstaviti iz tega imenika.
  • Ustvariti moramo funkcijo rokovanja, ki jo bo Lambda uporabljal za preizkus našega dogodka.

Naslednji delček vsebuje našo aplikacijo, prilagojeno za uporabo Lambda:

Kot vidite, je izvedba zelo podobna prejšnji. Spremenili smo le imenik, iz katerega smo naložili svoj vtičnik, in namesto tiskanja vrednosti dodali odziv funkcije. Če želite izvedeti več o pisanju Lambdas-a v golang, poglejte dokumentacijo AWS.

Uvajanje AWS Lambda

Obstajata dva načina uvajanja funkcij in slojev AWS Lambda. Paket z zadrgo lahko ustvarite in naložite ročno ali uporabite naprednejši okvir, kar omogoča veliko lažje in hitrejše delovanje. Za večino svojih projektov uporabljam ogrodje brez strežnika, zato sem s tem orodjem že pripravil preprosto konfiguracijsko datoteko serverless.yml:

storitev: cipherService
FrameworkVersion: "> = 1.28.0 <2.0.0"
ponudnik:
  ime: aws
  trajanje: go1.x
plasti:
  šifrirni sloj:
    pot: bin / plugin
    združljiv čas izvajanja:
      - go1.x
funkcije:
  motor:
    rokovalnik: koš / šifraEngine
    paket:
      izključi:
        - ./**
      vključujejo:
        - ./bin/cipherEngine
    plasti:
      - {Ref: CipherLayerLambdaLayer}

V razdelku plasti smo določili en sloj s potjo do že ustvarjenega vtičnika - nameščen bo skupaj s funkcijo lambda. Določite lahko do 5 različnih slojev, kateri vrstni red je res pomemben. Nameščeni so v isti / opt imenik, zato lahko plasti z večjim številom preglasijo datoteke iz predhodno nameščenih slojev. Za vsak sloj morate navesti vsaj 2 parametra: pot do imenika, ki vsebuje vir plasti (pot do binarnega vtičnika v vašem primeru) in seznam združljivih programov izvajanja.

Naslednji razdelek funkcij je mesto, kjer določite seznam funkcij, ki jih je treba uporabiti. Za vsako funkcijo morate navesti vsaj pot do sestavljene aplikacije. Poleg tega moramo določiti parameter plasti s sklicevanjem na zgornjo plast. To bo med uvajanjem samodejno pritrdilo plast na našo funkcijo Lambda. Smešno je, da morate pretvoriti ime svoje plasti lambda v TitleCased in dodati pripono LambdaLayer, če se želite sklicevati na ta vir. Zdi se, da ga je ekipa brez strežnika tako izvedla, da je rešila konflikt glede na različne vrste virov.

Ko je naša konfiguracijska datoteka serverless.yml pripravljena, je treba zadnjo stvar sestaviti našo aplikacijo, jo vstaviti in namestiti. Za to lahko uporabimo preprost Makefile:

.PHONY: zgraditi buildPlugin clean implementirati
sestaviti:
 dep zagotoviti -v
 env GOOS = linux go build -ldflags = "- s -w" -o bin / cipherEngine šifraEngine / main.go
buildPlugin:
 env GOOS = linux go build -ldflags = "- s -w" -buildmode = plugin -o bin / plugin / cipher.so ../plugin/cipher.go
čisto:
 rm -rf ./bin ./vendor Gopkg.lock
implementirati: čista buildPlugin build
 sls implementirati --verbose

Svojo funkcijo lahko sestavite in uporabite tako, da zaženete naslednji ukaz:

narediti uvajanja

Testna AWS Lambda

Kot sem že omenil, AWS Lambda v odzivu na dogodek izvrši kodo. Kljub temu nismo konfigurirali nobenega sprožilca dogodkov, zato ga brez naše pomoči ne bomo uporabili. To moramo storiti ročno s pomočjo ogrodja Serverless ali orodja awscli:

sls prikliče -f function_name
aws lambda invoke - ime-funkcije-ime-funkcije-ime-izhod_datoteke

V odgovoru bi morali videti enak izhod kot prej, kar dokazuje, da naša lambda funkcija deluje pravilno in naloži vtičnik iz dodatnega sloja. Zdaj lahko ustvarite druge funkcije, ki bodo uporabljale isti sloj ali ga celo delile z drugimi računi AWS.

Povzetek

Zelo zabavno je bilo uporabljati Golang module in preizkusiti, kako jih povezati z novo izdanimi AWS Lambda Layers. Knjižnica vtičnikov je res super, vendar se lahko zaradi svojih omejitev in specifikacije Golang uporablja le v nekaterih posebnih scenarijih. Mislim, da za večino razvijalcev, ki delajo na standardnih projektih, vtičnikov ne bo treba ali celo mogoče. Na misel mi prihajata le dva razloga:

  • Izvajanje zapletenih algoritmov, ki jih lahko uporabljajo druge aplikacije, npr. algoritmi za kodiranje ali šifriranje videoposnetkov.
  • Delite svoj algoritem z drugimi, ne da bi objavili njegovo kodo.