% !TeX root = ../thesis.tex
\chapter{Elméleti összefoglaló}
\label{sec:theory}

\section{Felhő alapú szolgáltatások rendszerezése}
A felhő alapú számítástechnikában \cite{cloud} a felhasználó elől elrejtve, a szolgáltató erőforrás halmazán elosztva megvalósított szolgáltatásokat értjük, amit jellemzően virtualizációs technológiára építenek. Négy szolgáltatási modellt különböztetünk meg: SaaS \cite{saas} (Software as a Service, Szoftver, mint Szolgáltatás, például: Office 365), FaaS \cite{faas} (Function as a Service, Függvény, mint Szolgáltatás, például: Amazon Lambda), PaaS \cite{paas} (Platform as a Service, Platform, mint Szolgáltatás, például: Oracle Cloud Platform) és IaaS \cite{iaas} (Infrastructure as a Service, Infrastruktúra, mint Szolgáltatás, például: Microsoft Azure). A tov\'abbiakban ezen szolg\'altat\'asmodellek angol nyelvű megnevez\'es\'et fogom haszn\'alni.

A Software as a Service szolgáltatási modellben a felhasználó egy kész szoftvercsomag használati jogát vásárolja meg vagy bérli. Ez azért felhő alapú szolgáltatás, mert a szoftver a szolgáltató infrastruktúráján fut. A végfelhasználóknak nincs rálátásuk a futó kódra vagy az infrastruktúrára. Ebből adódóan az üzemeltetési feladatok nem mérnöki jellegűek, legtöbbször csak a felhasználói fiókok adminisztrációjára van lehetőség. 

A Function as a Service nem csak egy szolgáltatási modell, hanem megkövetel egy bizonyos szoftverarchitektúrát is. Az FaaS-t használó szoftverek függvényekből állnak. Ezek hasonlóak a tradicionális szoftverekben ismeretes függvényekhez, annyi különbséggel, hogy a bemeneti paraméterekre és a visszatérési értékre szabhat megkötéseket egy FaaS platform. A feltöltött függvények egy URL-en érhetők el, melyeket megnyitva az adott függvény lefut. Erre a futásra rálátása a felhasználónak nincs, csak a visszatért eredményt kapja meg. A felhasználó számára még a futtató környezet is ismeretlen. Emiatt a függvényeket csak a szolgáltató által nyújtott platformon lehet futtatni, tesztelni. Ez, valamint a nagyszámú komponensre bontott szoftverarchitektúra megnehezíti a hibakeresést, és a hibák előfordulási okának megtalálását is.

Platform as a Service típusú szolgáltatások alatt értjük azon szolgáltatásokat, melyek lehetővé teszik egy elkészült alkalmazás futtatását egy, a szolgáltató által menedzselt platformon. A szolgáltatás felhasználójának csak a saját alkalmazásával felmerülő problémákat kell megoldania, a fizikai szervereket, operációs rendszert, valamint a middleware-t - ami lehet például Java futtatókörnyezet vagy Kubernetes konténer orkesztrációs platform - a szolgáltató biztosítja. Ezek mellett gyakran adatbázis-szolgáltatást is igénybe lehet venni. Egy PaaS platformon telepített alkalmazásban hibák keresése külön megfontolásokat nem igényel, a helyben és távolban futtatott példányok között nincsen különbség. 

Egy Infrastructure as a Service típusú szolgáltatás keretében a szolgáltató egy virtuális gépet nyújt a végfelhasználóknak. Erre a gépre tetszőleges operációs rendszer telepíthető. Ezt a szolgáltató legtöbb esetben legfeljebb monitoring lehetőségekkel bővíti. E szolgáltatási modell keretében üzemeltetett alkalmazással kapcsolatban fordul elő a legtöbb mérnöki probléma, ugyanis a hálózaton és a virtuális gépeket futtató szerverek nagy rendelkezésre állásán kívül a szolgáltató nem vállal semmilyen garanciát. Míg például a Platform as a Service szolgáltatások esetében az alkalmazás terheléstől függő skálázását a szolgáltató garantálta, erről és az ezzel kapcsolatban felmerülő problémák megoldásáról a felhasználónak kell gondoskodnia. Mindezért cserébe a felhasználónak behatása - illetve rálátása van a futtató környezetre.

\section{Konténerizáció}
A konténerizáció vagy operációs rendszer szintű virtualizáció \cite{os-virt} alatt egy fizikai vagy virtuális számítógépen futó operációs rendszer egymástól független partíciókra osztását értjük. Általában szerverek virtualizálására használják. Számítógépek virtualizációjától \cite{dockervirt} lényeges eltérés, hogy a kernel - az operációs rendszer hardware-t kezelő része - nem kell fusson minden példányon, viszont hasonlóság, hogy a dinamikusan csatolt osztott könyvtárak minden konténerben külön betöltésre kerülnek a memóriába. 

Az elmúlt években kifejezetten népszerűvé vált, ugyanis a saját fejlesztésű szoftvercsomagokból gyorsan létrehozható egy nem módosítható konténer kép, ami ezután rövid idő alatt példányosítható. Ezáltal a fejlesztői- és éles környezet teljesen ugyanaz lehet. További előnye, hogy egy szoftvercsomag gyorsan telepíthető, gyakran előre konfigurálva, anélkül, hogy bármi módosítást eszközölne a felhasználó a számítógépén. Természetesen erre van lehetőség virtuális gépekkel is, viszont egy-egy ilyen kép több helyet foglal, valamint futtatásához több erőforrásra is szükség van.

\subsection{Docker}
A legnépszerűbb megvalósítása az operációs rendszer szintű virtualizációnak a Docker \cite{docker-overview} - melyet a szakdolgozatomban használt Kubernetes rendszer is használ. A Docker kihasználja a Linux operációs rendszer által nyújtott szolgáltatásokat az egyes konténerek izolálásához. 

Konténer képek létrehozására két lehetőség van. Az egyik egy már meglévő konténer képből futó konténer létrehozása, a kívánt módosítások elvégzése, a leállt konténerről nem módosítható pillanatkép készítése. Másik lehetőség egy úgynevezett Dockerfile létrehozása, ahol a kiinduló konténer kép megadására, valamint a módosítások lépésenkénti megadására van lehetőség. Ezeket a lépéseket rétegezetten \cite{docker-layers} hajtja végre a Docker, azaz minden lépés eredménye egy kép, amit a rendszer példányosít és elvégzi a következő lépést. Ez lehetővé teszi a konténer kép építésének gyorsítását, ugyanis azokat a lépéseket nem szükséges újra végrehajtani, melyek eredménye nem változott. Fontos, hogy amennyiben egy réteg változik, az arra épülő rétegekhez tartozó lépéseket is újra végre kell hajtani. A Dockerfile használata lehetővé teszi a konténer képek létrehozásának automatizálását, melyet a szakdolgozatomban is kihasználtam.

\section{Kubernetes}
A Kubernetes egy Go nyelven írt, nyílt forráskódú konténer orkesztrációs platform, amely képes konténerek automatikus konfigurációjára, skálázására, valamint bizonyos hibák automatikus elhárítására is. Több konténer technológiát \cite{kubernetes-runtimes} támogat, köztük a Dockert is. Nagyon népszerű, gyors fejlesztés alatt álló projekt. Emiatt felhasználói és programozói interfésze gyakran változik, megkövetelve a ráépülő megoldásoktól a hasonló sebességű fejlesztést. Jól definiált interfésze miatt sok ráépülő, azt kiegészítő projekt létezik. Egy ilyen a Kubeless, amely segítségével Function as a Service megoldásokat lehet készíteni Kubernetes környezetben. 

Néhány fontosabb szolgáltatás, melyet a Kubernetes nyújt:
\begin{itemize}
 \item Horizontális skálázás,
 \item Konfiguráció és szenzitív adatok menedzsmentje,
 \item Háttértár orkesztráció
\end{itemize}

\subsection{Kubernetes klaszter felépítése}
Egy Kubernetes klaszterben két típusú hosztgép lehet. Mindkettőből lehet több darab, de legalább egy-egy példány kötelező. A \ref{fig:k8s-chart} \'abr\'an l\'athat\'o, hogy egy Kubernetes klaszter \cite{kubernetes-nodes} legal\'abb egy Masterből \'es Workerből \'ep\"ul fel, ezek egy-egy feladatot ell\'at\'o komponensekből \'allnak.

\begin{figure}[!ht]
\centering
\includegraphics[width=120mm, keepaspectratio]{figures/k8s_chart.png}
\caption{Egy Kubernetes klaszter fel\'ep\'it\'ese} 
\label{fig:k8s-chart}
\end{figure}

A Kubernetes Master felelős a klaszterben lezajló folyamatok \cite{kubernetes-concepts} irányításáért, a Slave-ek vagy más néven Worker-ek, valamint az alkalmazások állapotának nyilvántartásáért. A klaszterben történő eseményekre válaszul klaszterszintű választ ad - például egy pod elindítása. 

Egy Master node számos komponensből áll, ezek a Master egy-egy feladatáért felelnek. Több Master node futtatása esetén - úgynevezett multi-master mode - csak az API Server \cite{kube-apiserver} és az etcd \cite{etcd} komponensekből jön létre több példány, a többiből egyszerre csak egy példány lehet aktív.

\subsection{API Server}
Az API-Server szolgálja ki a Kubernetes API-t \cite{kubernetes-api}, amelyen keresztül lehet interakcióba lépni a klaszterrel. A kiszolgált API REST alapú, JSON objektumokba csomagolva lehet az etcd-ben lévő információt lekérdezni vagy frissíteni. Ez egy kifejezetten fontos része egy klaszternek, meghibásodása esetén a klaszter konfigurációja igen nehézkes.

\subsection{Etcd}
A CoreOS által fejlesztett, nyílt forráskódú elosztott kulcs-érték tár \cite{etcd}. Itt kerül tárolásra, illetve innen lehet lekérdezni a klaszter, valamint az egyes komponensek állapotát. Egyes komponensek figyelik az itt található, nekik fontos kulcsokhoz tartozó értékeket, változás esetén elvégzik az esetleges módosításokat.

\subsection{Controller Manager}
Logikailag különböző kontrollereket összefoglaló komponens \cite{kuebrnetes-controller}. Az alábbi kontrollereket a komplexitás csökkentése érdekében fordították egy binárisba:

\begin{itemize}
 \item Node Controller \cite{kubernetes-node-controller}: Egyes Node-ok \cite{kubernetes-nodes} elérhetetlenné válásának figyeléséért, erre történő reagálásért felelős.
 \item Replication Controller \cite{kuebrnetes-components}: A klaszterben megfelelő számú podok meglétéért felelős kontroller.
 \item Endpoints Controller: Service-ek és Podok társításáért felelős.
 \item Service Account \& Token Controllers: Alapértelmezett felhasználói fiókok és API tokenek létrehozását hajtja végre néhány Namespace-hez.
\end{itemize}

\subsection{Scheduler}
A Scheduler \cite{kubernetes-scheduler} vagy Ütemező figyeli, mely podok még nincsenek egy Slave node-hoz sem rendelve, majd hozzárendeli egyhez olyan módon, hogy a hozzárendelt node-on lévő erőforrások kielégítsék a pod igényeit, valamint a terhelés legyen lehetőség szerint egyenlően elosztva a node-ok között.

\subsection{Horizontal Pod Autoscaler}
A Horizontal Pod Autoscaler \cite{kubernetes-hpa} automatikusan skálázza a podok számát egy Deploymentben a megfigyelt CPU-használat alapján. Ez a megfigyelés 15 másodperces ciklusokban történik, majd a skálázási döntés a gyűjtött metrikák 1 perces átlaga alapján zajlik.

\subsection{Slave Node}
A Kubernetes klaszter azon részét, ahol a telepített alkalmazások futnak Slave Node-nak vagy bizonyos szakirodalomban Workernek \cite{kubernetes-nodes} hívják. Egy Slave Node komponenseit \aref{sec:container-runtime}, \aref{sec:kubelet} \'es \aref{sec:kube-proxy} alfejezetekben r\'eszletezem.

\subsection{Container Runtime}
\label{sec:container-runtime}
A konténerek futtatásáért felelős komponens. Képes használni többek között Docker, CRI-O és containerd konténer futtatási környezeteket.

\subsection{Kubelet}
\label{sec:kubelet}
A kubelet \cite{kubernetes-kubelet} felelőss\'ege, hogy a podok specifikációjuk szerinti állapotban fussanak. A klaszter összes tagján kötelezően fut.

\subsection{Kube-Proxy}
\label{sec:kube-proxy}
UDP vagy TCP forgalom továbbítására képes komponens \cite{kubernetes-kube-proxy}, amely minden Slave Node-on kötelezően fut.

\section{Kubernetes-ben létrehozható objektumok}
A Kubernetes-ben többek között az alábbi objektumok hozhatók létre:

\subsection{Pod}
A Pod \cite{kubernetes-pods} egy vagy több konténert összefogó logikai hoszt. Egy podon belül lévő konténerek osztoznak a hálózaton és a háttértáron, valamint azonos a futtatási specifikációjuk. Ez azt jelenti, hogy az egy podon belüli konténerek localhost-ként megtalálják egymást, valamint van lehetőség, hogy a konténerekben futó alkalmazások lássák a másik konténerben futó folyamatokat. Egy Kubernetes rendszerben a Pod a legkisebb egység, amit futásra lehet ütemezni.

\subsection{Deployment}
A Deployment \cite{kubernetes-deployment} segítségével deklaratívan leírható egy alkalmazást felépítő podok és azok kívánt állapota. Lehetőség van megadni, hány replikát hozzon létre a rendszer. Hasonló módon lehet a podok állapotát frissíteni vagy egy korábbi állapotra visszatérni. Egy Deploymentben lehetőség van több pod definiálására, ami az alkalmazás komponensek lazább csatolását teszi lehetővé.

\subsection{Service}
A podok bármikor törlődhetnek, valamint új példány jöhet belőlük létre \cite{kubernetes-service}. Minden pod saját IP címmel rendelkezik, viszont szükség van valamilyen módszerre, aminek segítségével nyomon lehet követni, hogy egy pod által nyújtott szolgáltatás milyen címen érhető el. Erre a problémára nyújt megoldást a Service, ami absztrakciót jelent a podok felett.

\subsection{Volume}
A perzisztens adattárolás \cite{kubernetes-volume} gyakori igény, főleg valamilyen állapotot számontartó alkalmazások esetében. A podok alapvetően nem alkalmasak erre, ezért szükség van a Volume-okra, ami lehetővé teszi a perzisztens adattárolást Kubernetes környezetben.

\subsection{Ingress}
Ingress \cite{kubernetes-ingress-resource} erőforrás segítségével klaszteren belüli Service erőforrást lehet azon kívülre kiszolgálni. Ennek módját az Ingress erőforrás határozza meg, amelyet az Ingress Controller \cite{kubernetes-ingress} nevű klaszter szintű objektum szolgál ki.

\section{Kubeless}
A Kubeless \cite{kubeless} egy Go nyelven írt, nyílt forr\'askódú, Kubernetes rendszerbe épülő Function as a Service megoldás. Számos ehhez hasonló rendszer létezik, a Kubeless különlegessége abban rejlik, hogy a funkcionalitásának kis részéhez használ újonnan bevezetett logikát, szinte mindent a Kubernetes API kiegészítésével ér el. A keretrendszer támogat számos népszerű programnyelvet, például a Go, a Python, a Java, a Javascript és a C\# nyelveket. 

Egy telepített függvény lefutását több esemény - úgynevezett trigger - kiválthatja. Ezek közül egy a http kérés \cite{kubeless-http}, amelyet a szakdolgozatomban vizsgáltam. Emellett van lehetőség eseményvezérelt műkődésre is \cite{kubeless-pubsub}, például Kafka rendszerben tárolt üzenetek feldolgozására is. 

Lévén, hogy Function as a Service rendszerről van szó, a Kubeless-be telepítendő függvényeket sajátos módon kell megírni. Ahogy \aref{code:hello-kubeless-go} k\'odr\'eszleten l\'athat\'o, hogy egy Kubeless specifikus csomagot kell import\'alni Go nyelven \'irt f\"uggv\'enyek eset\'eben.

\begin{lstlisting}[float=!ht,caption={Kubeless rendszerbe telep\'ithető Hello World k\'odr\'eszlet Go nyelven},label=code:hello-kubeless-go]
package kubeless

import (
	"github.com/kubeless/kubeless/pkg/functions"
)

func hello(event functions.Event, context functions.Context) (string, error) {
	return "Hello world!", nil
}
\end{lstlisting}

Mint \aref{code:hello-kubeless-go} kódrészleten is látszik, a függvény első paraméter\'eben megkapja a kiváltott eseményt, a másodikban pedig a futási kontextust, a visszatérése pedig egy karakterlánc, opcionálisan pedig egy keletkezett kivétel. Minden úgynevezett eseménykezelőnek ilyen szignatúrával kell rendelkeznie. Az eseményt leíró, functions. Event típusú paraméterben, például http kérés esetén annak törzsében található adat. 

Egy megírt függvényt telepíteni két módon lehet. Egyik lehetőség közvetlen a Kubernetes API-t \cite{kubeless-api-deploy} használva. Alternatíva és könnyítésként a Kubeless fejlesztői elkészítettek egy parancssoros programot, amelyet használva egyszerűen lehet telepíteni függvényeket, létrehozni triggereket, valamint beállítani a skálázást. Fontos, hogy telepítés közben nem jön létre automatikusan CPU limit egy-egy függvénynek, akkor sem, ha skálázást kérünk hozzá. Skálázáshoz a Kubeless a Horizontal Pod Autoscalert használja. 

Mivel a Kubernetes-ben podokat van lehetőség futtatni és ütemezni, a Kubeless függvényekből is podokat kell létrehozni. Ez a folyamat \cite{kubeless-build}, amely \aref{fig:kubeless-pod-creation} \'abr\'an megfigyelhető, részleteiben eltér programnyelvenként azok sajátosságai miatt. 

\begin{figure}[!ht]
\centering
\includegraphics[width=120mm, keepaspectratio]{figures/kubeless_pod_creation.png}
\caption{Kubeless f\"uggv\'enyből pod l\'etrehoz\'asa} 
\label{fig:kubeless-pod-creation}
\end{figure}

A podban futó konténer létrehozása során a Kubeless Controller a Debian nevű Docker képből indul ki. Először telepíti a programnyelv csomagjait, annak függőségeit és a kód binárissá fordításához szükséges eszközöket. Ezután felmásolja a kódot és a vele együtt, opcionálisan megadott függőségleíró állományt. A fordítási folyamat végén lefordítja a kódot. Ez a folyamat csak akkor lesz sikeres, ha a kód bel\'epési függvényét tartalmazó fájlban meg van jelölve a Kubeless futtató környezet, mint függőség, ezáltal nincs szükség egyedi fordítóeszközre. Az elkészült, futtatható binárist megjelöli a rendszer, mint a képből futtatott konténer belépési pontját. Egy így készült Docker képet lehetőség van feltölteni a Docker Hubra, így későbbi használat során nincs szükség a folyamat újbóli futtatására. 

Amennyiben http triggert hozunk létre egy függvényhez, létrejön egy Ingress objektum, amelyet kötelezően az NGINX Ingress Controller \cite{kubernetes-nginx} nevű Ingress Controller implementáció kell kiszolgálja, így annak telepítve kell lenni a klaszterben. Az Ingress Controller a megadott hosztnév - például function.example.com - alapján azonosítja, melyik függvényt kívánjuk meghívni. 

Mivel a függvényekből Kubernetes objektumok lesznek, a terheléselosztás a rendszerben már létező mechanizmusokkal történik. Egy függvényt kiszolgáló podok számának változása esetén a hozzájuk tartozó Ingress objektum nyomon követi a változást, így az NGINX Ingress Controller képes lesz a beérkező kérések elosztására.

\section{Istio}
Az Istio egy nyílt forráskódú, Kubernetes-be épülő hálózati forgalom menedzselését elősegítő platform. Segítségével csökkenthető a nagy számú komponensből álló alkalmazások komplexitása. 

Ezt a service mesh \cite{istio-service-mesh} koncepciójának bevezetésével éri el. A service mesh egy alkalmazást felépítő mikroszervizek és ezek közötti interakciók összességét jelenti. Ahogy egy service mesh nő méretében és komplexitásában, egyre nehezebb átlátni és menedzselni. Az Isitio betekintést ad \cite{istio-observer} és a belső működés irányítását \cite{istio-mgmt} nyújtja az egész service meshre. 

Az Istio többek között képes:

\begin{itemize}
 \item forgalom irányítására,
 \item autentikáció, autorizáció és titkosítás biztosítására,
 \item házirendek definiálására, azok érvényesítésére,
 \item automatikus monitoringra és naplózásra az alkalmazás komponenseknek fut\'as\'anak.
\end{itemize}

Szakdolgozatomban, közvetve az Istio terheléskiegyenlítő szolgáltatását is megvizsgálom, lévén, hogy a Knative azt használja, mint load balancert. 

\section{Knative}
A Knative \cite{knative} egy nyílt forráskódú, a Google által fejlesztett keretrendszer, amely a Kubernetesnél magasabb szintű absztrakciókat nyújt. Számos komponenséből a szakdolgozatban a serverless applikációk Kubernetes-be telepítését, futtatását megkönnyítő, úgynevezett Serving \cite{knative-serving} modult vizsgálom. Ezen kívül létezik még egy Eventing \cite{knative-eventing} komponens, amely eseményvezérelt alkalmazások fejlesztéséhez biztosít segédeszközöket. 

Nem kifejezetten Function as a Service megoldásról van szó \cite{knative-thoughts}, a nullára skálázás miatt emlegetik a Platform as a Service infrastruktúrák következő generációjaként, de funkcionalitása és működése remekül illeszkedik a FaaS szolgáltatásmodellhez is. Emellett a Kubernetes-ben már futó alkalmazásokat Knative-ba átrakni nem jelent szignifikáns munkát. Az érintett komponensek módosítására nincs szükség, csupán a Deploymenteket kell Knative Service-ekre átírni. Ezzel szemben a plusz funkciók, melyeket az átállással ki lehet használni jelentős előnyt jelentenek. 

Mint kor\'abban eml\'itettem, lényeges újítás a tradicionális Kubernetes-hez képest az egyes alkalmazáskomponensek nullára skálázása, valamint a konkurencia alapú skálázás. Mindkettőt a magasabb szintű absztrakció teszi lehetővé, ugyanis bár ezek Knative nélkül is elképzelhető funkciók, ezek megvalósítása számos extra komponens bevezetését igényelné. A nullára skálázáshoz szükséges egy perzisztensen létező egység, a Knative esetében az Istio, valamint a Knative Shared Gateway \cite{knative-gateweay} nevű komponens töltik be ezen egység szerepét. Konkurencia alapú skálázás esetében is ugyanez a komponens végzi a kérések elosztását. Az egy podra eső átlagos konkurens kérések megfigyeléséért egy úgynevezett Knative Autoscaler \cite{knative-autoscaler} felel. Ez az egység hozza a fel- és leskálázási döntéseket, valamint a megfigyelt konkurencia érték alapján a pánik ablak \cite{knative-autoscaler-component} kezdetét és végét.

A pánik ablak akkor lép érvénybe, ha rövid idő alatt nagy terhelés érkezik egy végpontra. Konkrétan a Service létrehozása során megadott célkonkurencia érték kétszerese \'erkezik, kevesebb, mint 6 másodperc alatt. Csak a Knative által bevezetett, konkurencia - azaz egy Service-hez egyidőben beérkező kérések száma - alapú skálázás esetében értelmezhető a pánik ablak. Ekkor viszont nincs lehetőség nullára skálázásra, ugyanis legalább egy Podnak mindig léteznie kell. Pánik ablak során a Knative a konkurencia alapján kiszámolt szükséges podok számának kétszeresét hozza létre. Vagy a terhelés stabilizálódása vagy 60 másodperc elteltével a podok száma visszatér a megfigyelt stabil konkurencia alapján szükséges számúra. Az aktuális konkurencia kiszámítása a Service által létrehozott podokra átlagolva kerül kiszámításra. Ebből a szükséges podok számát az észlelt konkurenciát a Service létrehozása során megadott célkonkurenciával elosztva számolja ki a rendszer. 

A Knative automatikusan elvégzi az Istio service mesh létrehozását minden telepített alkalmazáshoz, valamint a konfigurációjának frissen tartását, ezzel a felhasználóknak csak kivételes esetekben kell foglalkoznia. Lehetőség van Istio helyett Gloo \cite{knative-gloo} használatára terheléskiegyenlítőként, de ilyenkor nem minden funkció érhető el. Előnye, hogy kevesebb erőforrást használ, mint az Istio. A szakdolgozatban azért döntöttem az előbbi használata mellett, mert úgy véltem a Knative fejlesztők azt helyezték fókuszba, azt támogatják. További kutatás tárgya lehet a két load balancer közti különbségek vizsgálata. 

Opcionálisan telepíthető monitoring eszközök segítségével megfigyelhetők a rendszer belső folyamatai, állapotai. Például lehetőség van megfigyelni egyebek mellett egyes függvények és Knative rendszer elemek processzor és memóriahasználatát \cite{knative-monitoring}, a skálázást végző komponens állapotát. A Knative Monitoring rendszere a megfigyelésre a Prometheus-t, vizualizációra a Grafana nevű szoftver használja. A naplóállományok feldolgozására Logstash-t és Elasticsearch-öt, az ezekből kinyert metrikák vizualizálására Kibana-t használ a rendszer. Beállítástól függően, de alapértelmezetten másodperces gyakorisággal vesz a Prometheus mintát a Knative állapotáról. Ez, illetve a Logstash folyamatok számottevő Input/Output műveletet generál, amely a klaszter teljesítményére negatív hatással lehet. 

A Serving komponens a Kubernetes és az Istio már meglévő szolgáltatásait felhasználva, azokra építve nyújtja többletszolgáltatásait. A Kubernetes API-t kiegészítve bevezet néhány új objektumtípust \cite{knative-crd}, melyeket \aref{sec:service} pontt\'ol \aref{sec:revision} pontig r\'eszletezek.

\subsection{Service}
\label{sec:service}
Egy alkalmazás vagy egy alkalmazáskomponens leírására egyetlen absztrakciót biztosít. A Knative-ban a Service egy Route-ra és egy Configurationre képződik le, valamint ezek orkesztrálását végzi. E két objektummal teljesen kiváltható a használata. A belső objektumok állapotait a Service kontrollere továbbítja a Kubernetes API-n keresztül, mintha sajátja lenne.

\subsection{Route}
A Route vagy útvonal egy hálózati végpontot biztosít egy alkalmazáshoz. Ez egy hosszú életű, stabil, http protokollon keresztül elérhető végpontot jelent, amelyet egy vagy több Revision szolgál ki. Alapértelmezés szerint a legfrissebb Revision felé irányítja a forgalmat a rendszer, de van lehetőség több ilyen objektum között elosztani a forgalmat bizonyos százalékos arányban. Hasonlóan, egy Route képes minden mögötte lévő Revision számára a rendszeren kívülről is elérhető aldomain-t allokálni. 

Ez a funkcionalitás hasonlít a Kubernetes Service objektuméra, valamint az Ingress objektum bizonyos funkcióit is tartalmazza, adaptálja a Knative rendszerre.

\subsection{Configuration}
Szükség van alkalmazások, azok komponenseinek elvárt állapotának leírására. Kubernetes rendszerben erre a Deployment szolgál, ennek párja a Knative-ban a Configuration. Emellett ez az objektum tartja számon és hozza létre a Revisionöket, ahogy az elvárt állapot módosul.

\subsection{Revision}
\label{sec:revision}
A Revision egy nem módosítható verziója egy alkalmazás kódjának, valamint konfigurációjának. Ez a gyakorlatban egy konténer képet jelent. Létrehozásuk a megfelelő Configuration objektum módosításával lehetséges. 

Azok a Revisionök, melyek nem érhetők el egy Route-on keresztül sem, törlésre kerülnek. Viselkedésük hasonló a podokéhoz, ilyen objektumokra képződnek le.
