ProHoster > Blogi > Haldamine > Optimeeritud Dockeri piltide loomine kevadise käivitamise rakenduse jaoks
Optimeeritud Dockeri piltide loomine kevadise käivitamise rakenduse jaoks
Konteinerid on muutunud eelistatud vahendiks rakenduse pakendamiseks koos kõigi selle tarkvara- ja operatsioonisüsteemisõltuvustega ning seejärel erinevatesse keskkondadesse toimetamiseks.
See artikkel hõlmab erinevaid võimalusi Spring Booti rakenduse konteinerisse paigutamiseks:
Dockeri kujutise loomine dockeri faili abil,
OCI-pildi loomine allikast Cloud-Native Buildpacki abil,
ja pildi optimeerimine käitusajal, eraldades JAR-i osad erinevateks tasemeteks, kasutades kihilisi tööriistu.
Koodi näide
Selle artikliga on kaasas töötav koodinäide GitHubis .
Konteinerite terminoloogia
Alustame kogu artiklis kasutatud konteinerterminoloogiaga:
Konteineri mootor: konteineri käitamise eest vastutav deemonprotsess.
Konteineri host: hostmasin, millel konteineri mootor töötab.
Konteinerite register: konteineri kujutise avaldamiseks ja levitamiseks kasutatav üldine asukoht.
OCI standard: Avatud konteinerite algatus (OCI) on kerge avatud lähtekoodiga haldusraamistik, mille on moodustanud Linux Foundation. OCI kujutise spetsifikatsioon määratleb konteineri kujutise vormingute ja käitusaja standardid, et kõik konteinerimootorid saaksid käitada mis tahes ehitustööriistaga loodud konteineri kujutisi.
Rakenduse konteinerisse paigutamiseks mähime oma rakenduse konteineri kujutisse ja avaldame selle pildi avalikus registris. Konteineri käitusaeg hangib selle pildi registrist, pakib selle lahti ja käivitab selle sees oleva rakenduse.
Spring Booti versioon 2.3 pakub pistikprogramme OCI-piltide loomiseks.
laevalaadija on kõige sagedamini kasutatav konteineri rakendus ja me kasutame oma näidetes Dockerit, nii et kõik järgnevad konteineri viited selles artiklis viitavad Dockerile.
Konteinerpildi loomine traditsioonilisel viisil
Dockeri piltide loomine Spring Booti rakenduste jaoks on väga lihtne, lisades oma Dockerfile'i mõned juhised.
Esmalt loome käivitatava JAR-i ja osana Dockerfile'i juhistest kopeerime käivitatava JAR-i pärast vajalike kohanduste rakendamist JRE põhipildi peale.
Loome oma kevadise rakenduse Kevadine algseade sõltuvustega web, lombokи actuator. Lisame API pakkumiseks ka puhkekontrolleri GETmeetod.
Dockeri faili loomine
Seejärel asetame selle rakenduse lisamise teel konteinerisse Dockerfile:
Meie Dockerfile sisaldab põhipilti, alates adoptopenjdk, mille peale kopeerime oma JAR-faili ja avame seejärel pordi, 8080mis kuulab taotlusi.
Rakenduse kokkupanek
Kõigepealt peate looma rakenduse Maven või Gradle abil. Siin kasutame Mavenit:
mvn clean package
See loob rakenduse jaoks käivitatava JAR-faili. Dockeri mootoris töötamiseks peame selle käivitatava JAR-i teisendama Dockeri pildiks.
Loo konteineri pilt
Seejärel paneme selle JAR-i käivitatava faili Dockeri pildile, käivitades käsu docker buildvarem loodud Dockerfile'i sisaldava projekti juurkataloogist:
docker build -t usersignup:v1 .
Näeme oma pilti loendis käsuga:
docker images
Ülaltoodud käsu väljund sisaldab meie pilti usersignupkoos põhipildiga, adoptopenjdktäpsustatud meie Dockerfile'is.
REPOSITORY TAG SIZE
usersignup v1 249MB
adoptopenjdk 11-jre-hotspot 229MB
Vaadake konteineri kujutise sees olevaid kihte
Vaatame pildi sees olevat kihtide virna. Me kasutame tööriist sukelduma, nende kihtide vaatamiseks:
dive usersignup:v1
Siin on osa sukeldumiskäsu väljundist:
Nagu näeme, moodustab rakenduse kiht olulise osa pildi suurusest. Soovime optimeerimise osana järgmistes jaotistes selle kihi suurust vähendada.
Konteineri kujutise loomine Buildpacki abil
Komplekteerimispaketid (Ehituspakid) on üldtermin, mida kasutavad erinevad platvormi teenusena (PAAS) pakkumised lähtekoodist konteineri kujutise loomiseks. Selle käivitas Heroku 2011. aastal ja sellest ajast alates on selle kasutusele võtnud Cloud Foundry, Google App Engine, Gitlab, Knative ja mõned teised.
Cloud Build pakettide eelis
Kujutiste koostamiseks Buildpacki kasutamise üks peamisi eeliseid on see pildi konfiguratsiooni muudatusi saab hallata tsentraalselt (ehitaja) ja levitada kõikidesse ehitajat kasutavatesse rakendustesse.
Ehituspaketid olid platvormiga tihedalt seotud. Cloud-Native Buildpackid pakuvad platvormide standardimist, toetades OCI pildivormingut, mis tagab, et pilti saab käitada Dockeri mootor.
Spring Boot Plugina kasutamine
Spring Booti pistikprogramm loob OCI-kujutisi allikast, kasutades Buildpacki. Pildid luuakse kasutades bootBuildImageülesanded (Gradle) või spring-boot:build-imagesihtmärk (Maven) ja kohalik Dockeri installimine.
Saame kohandada pildi nime, mida peame Dockeri registrisse lükkama, määrates nime image tag:
Järgmisena käivitame rakenduse koostamiseks ja konteineri kujutise loomiseks käsu Maven abil pistikprogrammi Jib. Nagu varemgi, ei kasuta me siin ühtegi Docker-faili:
Pärast ülaltoodud Maven käsu täitmist saame järgmise väljundi:
[INFO] Containerizing application to pratikdas/usersignup:v1...
.
.
[INFO] Container entrypoint set to [java, -cp, /app/resources:/app/classes:/app/libs/*, io.pratik.users.UsersignupApplication]
[INFO]
[INFO] Built and pushed image as pratikdas/usersignup:v1
[INFO] Executing tasks:
[INFO] [==============================] 100.0% complete
Väljund näitab, et konteineri kujutis on loodud ja registrisse paigutatud.
Motivatsioonid ja meetodid optimeeritud piltide loomiseks
Meil on optimeerimiseks kaks peamist põhjust:
Производительность: konteineri orkestreerimissüsteemis tõmmatakse konteineri kujutis pildiregistrist konteinerimootorit käitavasse hosti. Seda protsessi nimetatakse planeerimiseks. Suurte kujutiste tõmbamine registrist toob kaasa pikad ajastamisajad konteinerite orkestreerimissüsteemides ja pikad ehitusajad CI torujuhtmetes.
turvalisus: suurtel piltidel on ka suur ala turvaaukude jaoks.
Dockeri pilt koosneb kihtide virnast, millest igaüks esindab avaldust meie Dockerfile'is. Iga kiht tähistab aluskihi muutuste deltat. Kui tõmbame registrist Dockeri pildi, tõmmatakse see kihtidena ja salvestatakse hosti vahemällu.
Spring Boot kasutab "paks JAR" sisse vaikepakendivorminguna. Kui vaatame paksu JAR-i, näeme, et rakendus on väga väike osa kogu JAR-ist. See on osa, mis muutub kõige rohkem. Ülejäänud osa koosneb Spring Frameworki sõltuvustest.
Optimeerimisvalem keskendub rakenduse eraldamisele Spring Frameworki sõltuvustest eraldi tasemel.
Sõltuvuskiht, mis moodustab suurema osa paksust JAR-failist, laaditakse alla ainult üks kord ja salvestatakse hostsüsteemi vahemällu.
Rakenduse värskendamise ja konteineri ajastamise ajal tõmmatakse rakendusest ainult õhuke kiht, nagu on näidatud sellel diagrammil:
Järgmistes jaotistes vaatleme, kuidas neid optimeeritud pilte Spring Booti rakenduse jaoks luua.
Kevadkäivitusrakenduse jaoks optimeeritud konteinerpildi loomine koos Buildpackiga
Spring Boot 2.3 toetab kihistamist, eraldades paksu JAR-faili osad eraldi kihtideks. Kihistamise funktsioon on vaikimisi keelatud ja see tuleb Spring Boot Maven pistikprogrammi abil selgesõnaliselt lubada:
Kui käivitame Dive'i, et näha saadud pildil olevaid kihte, näeme, et rakendusekiht (punase ringiga) on kilobaidivahemikus palju väiksem kui paksu JAR-vorminguga.
Dockeriga kevadkäivitusrakenduse jaoks optimeeritud konteinerpildi loomine
Maveni või Gradle'i pistikprogrammi asemel saame luua ka Dockeri failiga kihilise Dockeri JAR-kujutise.
Dockeri kasutamisel peame kihtide eraldamiseks ja lõplikule pildile kopeerimiseks tegema kaks lisatoimingut.
Saadud JAR-i sisu näeb pärast Maveni ehitamist koos lubatud kihilisusega välja järgmine:
Väljund näitab täiendavat JAR-i nimega spring-boot-jarmode-layertoolsи layersfle.idxfaili. See täiendav JAR-fail pakub kihistamise võimalusi, nagu on kirjeldatud järgmises jaotises.
Eraldi kihtide sõltuvuste eraldamine
Meie kihilise JAR-i kihtide vaatamiseks ja ekstraktimiseks kasutame süsteemi atribuuti -Djarmode=layertoolsalustuseks spring-boot-jarmode-layertoolsJAR rakenduse asemel:
Selle käsu käivitamine annab väljundi, mis sisaldab saadaolevaid käsuvalikuid:
Usage:
java -Djarmode=layertools -jar usersignup-0.0.1-SNAPSHOT.jar
Available commands:
list List layers from the jar that can be extracted
extract Extracts layers from the jar for image creation
help Help about any command
Näeme loendit sõltuvustest, mida saab kihtidena lisada.
Vaikimisi kihid:
Kihi nimi
Sisu
dependencies
mis tahes sõltuvus, mille versioon ei sisalda SNAPSHOTI
spring-boot-loader
JAR-laaduri klassid
snapshot-dependencies
mis tahes sõltuvus, mille versioon sisaldab SNAPSHOTI
application
rakendusklassid ja ressursid
Kihid on määratletud layers.idxfaili selles järjekorras, milles need tuleks Dockeri pildile lisada. Need kihid salvestatakse hosti vahemällu pärast esimest toomist, kuna need ei muutu. Hostisse laaditakse alla ainult värskendatud rakendusekiht, mis on vähendatud suuruse tõttu kiirem .
Kujutise loomine, mille sõltuvused on eraldatud eraldi kihtidesse
Ehitame lõpliku pildi kahes etapis, kasutades meetodit nimega mitmeastmeline kokkupanek . Esimeses etapis eraldame sõltuvused ja teises etapis kopeerime eraldatud sõltuvused lõppu.
Muutkem oma Docker-faili mitmeetapilise ehituse jaoks:
# the first stage of our build will extract the layers
FROM adoptopenjdk:14-jre-hotspot as builder
WORKDIR application
ARG JAR_FILE=target/*.jar
COPY ${JAR_FILE} application.jar
RUN java -Djarmode=layertools -jar application.jar extract
# the second stage of our build will copy the extracted layers
FROM adoptopenjdk:14-jre-hotspot
WORKDIR application
COPY --from=builder application/dependencies/ ./
COPY --from=builder application/spring-boot-loader/ ./
COPY --from=builder application/snapshot-dependencies/ ./
COPY --from=builder application/application/ ./
ENTRYPOINT ["java", "org.springframework.boot.loader.JarLauncher"]
Salvestame selle konfiguratsiooni eraldi faili - Dockerfile2.
Ehitame Dockeri pildi käsuga:
docker build -f Dockerfile2 -t usersignup:v1 .
Pärast selle käsu täitmist saame järgmise väljundi:
Sending build context to Docker daemon 20.41MB
Step 1/12 : FROM adoptopenjdk:14-jre-hotspot as builder
14-jre-hotspot: Pulling from library/adoptopenjdk
.
.
Successfully built a9ebf6970841
Successfully tagged userssignup:v1
Näeme, et Dockeri pilt luuakse pildi ID-ga ja seejärel märgistatakse.
Lõpuks käivitame käsu Sukeldumine nagu varem, et kontrollida loodud Dockeri pildi sees olevaid kihte. Sukeldumiskäsule saame sisestada pildi ID või sildi:
dive userssignup:v1
Nagu väljundist näha, on rakendust sisaldav kiht nüüd vaid 11 KB ja sõltuvused on vahemällu salvestatud eraldi kihtidena.
Eraldi kihtidest eraldage sisemised sõltuvused
Rakenduskihi suurust saame veelgi vähendada, eraldades kõik oma kohandatud sõltuvused eraldi kihiks, selle asemel, et pakkida need koos rakendusega, deklareerides need ymlsarnase faili nimega layers.idx:
Selles failis layers.idxoleme lisanud kohandatud sõltuvuse nimega, io.myorgmis sisaldab jagatud hoidlast alla laaditud organisatsiooni sõltuvusi.
Väljund
Selles artiklis vaatlesime Cloud-Native Buildpacksi kasutamist konteineri kujutise loomiseks otse allikast. See on alternatiiv Dockeri kasutamisele konteineri kujutise loomiseks tavapärasel viisil: esmalt luuakse paks käivitatav JAR-fail ja seejärel pakitakse see konteineri kujutiseks, täpsustades Dockerfile'is olevaid juhiseid.
Samuti uurisime oma konteineri optimeerimist, lisades kihistamisfunktsiooni, mis eraldab sõltuvused eraldi kihtideks, mis salvestatakse hosti vahemällu, ja õhuke rakenduskiht laaditakse ajastamisajal konteineri täitmismootoritesse.
Kogu artiklis kasutatud lähtekoodi leiate aadressilt Github .
Käskude viide
Siin on kiire ülevaate saamiseks selles artiklis kasutatud käskude kokkuvõte.
Konteksti tühjendamine:
docker system prune -a
Konteineri kujutise loomine Dockerfile'iga:
docker build -f <Docker file name> -t <tag> .
Ehitage konteineri kujutis allikast (ilma Dockerfile'ita):
mvn spring-boot:build-image
Vaata sõltuvuskihte. Enne rakenduse jar-faili loomist veenduge, et kihistamise funktsioon oleks pluginas spring-boot-maven-plugin lubatud:
java -Djarmode=layertools -jar application.jar list
Sõltuvuskihtide eraldamine. Enne rakenduse jar-faili loomist veenduge, et kihistamise funktsioon oleks pluginas spring-boot-maven-plugin lubatud: