{"id":76769,"date":"2020-04-04T13:42:27","date_gmt":"2020-04-04T11:42:27","guid":{"rendered":"https:\/\/prohoster.info\/blog\/administrirovanie\/content-based-tagging-v-sborshhike-werf-zachem-i-kak-eto-rabotaet"},"modified":"2020-04-04T13:42:27","modified_gmt":"2020-04-04T11:42:27","slug":"content-based-tagging-v-sborshhike-werf-zachem-i-kak-eto-rabotaet","status":"publish","type":"post","link":"https:\/\/prohoster.info\/de\/blog\/administrirovanie\/content-based-tagging-v-sborshhike-werf-zachem-i-kak-eto-rabotaet","title":{"rendered":"Content-basiertes Tagging im Werfer: Warum und wie funktioniert das?","gt_translate_keys":[{"key":"rendered","format":"text"}]},"content":{"rendered":"<p><img decoding=\"async\" alt=\"Content-basiertes Tagging im Werfer: Warum und wie funktioniert das?\" src=\"\/wp-content\/uploads\/2020\/04\/494346bbee96cc2b6c838491ba1c67fb.jpg\" style=\"display:block;margin: 0 auto;\" \/><br \/>\n<br \/>\n<noindex><a rel=\"nofollow\" href=\"https:\/\/werf.io\/\">werf<\/a><\/noindex> \u2014 unser GitOps CLI-Tool mit offenem Quellcode zum Erstellen und Bereitstellen von Anwendungen in Kubernetes. In <noindex><a rel=\"nofollow\" href=\"https:\/\/habr.com\/ru\/company\/flant\/blog\/493170\/\">der Version v1.1<\/a><\/noindex> wurde eine neue Funktion im Image-Builder eingef\u00fchrt: die Tagging-M\u00f6glichkeit basierend auf dem Inhalt oder <i>inhaltsbasiertes Tagging<\/i>. Bislang bestand das typische Tagging-Schema in werf darin, Docker-Images nach Git-Tag, Git-Branch oder Git-Commit zu taggen. Doch alle diese Ans\u00e4tze haben M\u00e4ngel, die durch die neue Tagging-Strategie vollst\u00e4ndig behoben werden. Weitere Details dazu und warum sie so vorteilhaft ist \u2014 im Folgenden.<noindex><a rel=\"nofollow\" name=\"habracut\"><\/a><\/noindex><\/p>\n<h2>Deployment eines Satzes von Microservices aus einem Git-Repository<\/h2>\n<p>\nEs kommt h\u00e4ufig vor, dass eine Anwendung in mehrere mehr oder weniger unabh\u00e4ngige Dienste unterteilt ist. Die Releases dieser Dienste k\u00f6nnen unabh\u00e4ngig voneinander stattfinden: Es kann gleichzeitig ein oder mehrere Dienste released werden, w\u00e4hrend die anderen weiterhin ohne \u00c4nderungen funktionieren m\u00fcssen. Aus Sicht der Codeverwaltung und Projektorganisation ist es jedoch sinnvoller, solche Dienste der Anwendung in einem einzigen Repository zu halten.<\/p>\n<p>Es gibt Situationen, in denen Dienste tats\u00e4chlich unabh\u00e4ngig sind und nicht mit einer einzigen Anwendung verbunden sind. In diesem Fall werden sie in separaten Projekten platziert, und ihre Ver\u00f6ffentlichung erfolgt \u00fcber separate CI\/CD-Prozesse in jedem der Projekte.<\/p>\n<p>In Wirklichkeit teilen Entwickler jedoch oft eine gesamte Anwendung in mehrere Mikrodienste auf, und es w\u00e4re ein klarer Overkill, f\u00fcr jeden einzelnen einen separaten Repository und ein Projekt zu erstellen... Genau um diese Situation wird es im Folgenden gehen: Mehrere solcher Mikrodienste liegen in einem einzigen Repository des Projekts, und die Ver\u00f6ffentlichungen erfolgen \u00fcber einen einzigen Prozess in CI\/CD.<\/p>\n<h3>Tagging nach Git-Branch und Git-Tag<\/h3>\n<p>\nAngenommen, die am weitesten verbreitete Tagging-Strategie wird verwendet \u2014 <i>tag-or-branch<\/i>. F\u00fcr Git-Branches werden die Images mit dem Namen des Branches getaggt, zu einem bestimmten Zeitpunkt existiert f\u00fcr einen Branch nur ein ver\u00f6ffentlichtes Image mit diesem Namen. F\u00fcr Git-Tags werden die Images entsprechend dem Namen des Tags getaggt.<\/p>\n<p>Beim Erstellen eines neuen Git-Tags \u2014 beispielsweise beim erscheinen einer neuen Version \u2014 wird f\u00fcr alle Images des Projekts im Docker-Registry ein neuer Docker-Tag erstellt:<\/p>\n<ul>\n<li> <code>myregistry.org\/myproject\/frontend:v1.1.10<\/code><\/li>\n<li> <code>myregistry.org\/myproject\/myservice1:v1.1.10<\/code><\/li>\n<li> <code>myregistry.org\/myproject\/myservice2:v1.1.10<\/code><\/li>\n<li> <code>myregistry.org\/myproject\/myservice3:v1.1.10<\/code><\/li>\n<li> <code>myregistry.org\/myproject\/myservice4:v1.1.10<\/code><\/li>\n<li> <code>myregistry.org\/myproject\/myservice5:v1.1.10<\/code><\/li>\n<li> <code>myregistry.org\/myproject\/database:v1.1.10<\/code><\/li>\n<\/ul>\n<p>\nDiese neuen Image-Namen gelangen \u00fcber Helm-Vorlagen in die Kubernetes-Konfiguration. Beim Starten des Deployments mit dem Befehl <code>werf deploy<\/code> wird das Feld <code>image<\/code> in den Ressourcen-Manifests von Kubernetes aktualisiert und die entsprechenden Ressourcen aufgrund des ge\u00e4nderten Image-Namens neu gestartet.<\/p>\n<p><b>Das Problem<\/b>: wenn sich der Inhalt des Images im Vergleich zur vorherigen Version (Git-Tag) tats\u00e4chlich nicht ge\u00e4ndert hat, sondern nur das Docker-Tag, kommt es zu <i>einem unn\u00f6tigen<\/i> Neustart dieser Anwendung und somit kann es zu einem gewissen Stillstand kommen. Obwohl es keine wirklichen Gr\u00fcnde gab, diesen Neustart durchzuf\u00fchren.<\/p>\n<p>Folglich muss man bei dem aktuellen Tagging-Schema mehrere separate Git-Repositories verwalten, und es entsteht das Problem der Organisation der Bereitstellung dieser mehreren Repositories. Insgesamt wird ein solches Schema \u00fcberladen und kompliziert. Es ist besser, viele Dienste in einem einzigen Repository zu b\u00fcndeln und Docker-Tags zu erstellen, um unn\u00f6tige Neustarts zu vermeiden.<\/p>\n<h3>Tagging nach Git-Commit<\/h3>\n<p>\nIn werf gibt es auch eine Tagging-Strategie, die mit Git-Commits verbunden ist.<\/p>\n<p>Ein Git-Commit ist eine Identifikation des Inhalts eines Git-Repositorys und h\u00e4ngt von der Historie der Datei\u00e4nderungen im Git-Repository ab. Daher erscheint es sinnvoll, ihn zum Taggen von Images im Docker-Registry zu verwenden.<\/p>\n<p>Das Taggen nach Git-Commits hat jedoch die gleichen Nachteile wie das Taggen nach Git-Branches oder Git-Tags:<\/p>\n<ul>\n<li> Es k\u00f6nnte ein leerer Commit erstellt worden sein, der keine Dateien \u00e4ndert, w\u00e4hrend der Docker-Tag des Images ge\u00e4ndert wird.<\/li>\n<li> Es k\u00f6nnte ein Merge-Commit erstellt worden sein, der keine Dateien \u00e4ndert, w\u00e4hrend der Docker-Tag des Images ge\u00e4ndert wird.<\/li>\n<li> Es k\u00f6nnte ein Commit erstellt worden sein, der die Dateien in Git \u00e4ndert, die nicht im Image importiert werden, w\u00e4hrend der Docker-Tag des Images erneut ge\u00e4ndert wird.<\/li>\n<\/ul>\n<p><\/p>\n<h2>Das Taggen nach dem Namen des Git-Branches spiegelt nicht die Version des Images wider.<\/h2>\n<p>\nEs gibt ein weiteres Problem, das mit der Tagging-Strategie nach Git-Branches verbunden ist.<\/p>\n<p>Das Taggen nach dem Namen des Branches funktioniert, solange die Commits dieses Branches chronologisch aufeinanderfolgend gesammelt werden.<\/p>\n<p>\u0415\u0441\u043b\u0438 \u0432 \u0442\u0435\u043a\u0443\u0449\u0435\u0439 \u0441\u0445\u0435\u043c\u0435 \u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u0435\u043b\u044c \u0437\u0430\u043f\u0443\u0441\u0442\u0438\u0442 \u043f\u0435\u0440\u0435\u0441\u0431\u043e\u0440\u043a\u0443 \u0441\u0442\u0430\u0440\u043e\u0433\u043e \u043a\u043e\u043c\u043c\u0438\u0442\u0430, \u0441\u0432\u044f\u0437\u0430\u043d\u043d\u043e\u0433\u043e \u0441 \u043d\u0435\u043a\u043e\u0442\u043e\u0440\u043e\u0439 \u0432\u0435\u0442\u043a\u043e\u0439, \u0442\u043e werf \u043f\u0435\u0440\u0435\u0442\u0440\u0435\u0442 \u043e\u0431\u0440\u0430\u0437 \u043f\u043e \u0441\u043e\u043e\u0442\u0432\u0435\u0442\u0441\u0442\u0432\u0443\u044e\u0449\u0435\u043c\u0443 Docker-\u0442\u0435\u0433\u0443 \u0432\u043d\u043e\u0432\u044c \u0441\u043e\u0431\u0440\u0430\u043d\u043d\u043e\u0439 \u0432\u0435\u0440\u0441\u0438\u0435\u0439 \u043e\u0431\u0440\u0430\u0437\u0430 \u0434\u043b\u044f \u0441\u0442\u0430\u0440\u043e\u0433\u043e \u043a\u043e\u043c\u043c\u0438\u0442\u0430. \u0418\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u044e\u0449\u0438\u0435 \u044d\u0442\u043e\u0442 \u0442\u0435\u0433 Deployment&#8217;\u044b \u0441 \u044d\u0442\u043e\u0433\u043e \u043c\u043e\u043c\u0435\u043d\u0442\u0430 \u0440\u0438\u0441\u043a\u0443\u044e\u0442 \u0432\u043e \u0432\u0440\u0435\u043c\u044f \u043f\u0435\u0440\u0435\u0437\u0430\u043f\u0443\u0441\u043a\u0430 pod&#8217;\u043e\u0432 \u0441\u0434\u0435\u043b\u0430\u0442\u044c pull \u0434\u0440\u0443\u0433\u043e\u0439 \u0432\u0435\u0440\u0441\u0438\u0438 \u043e\u0431\u0440\u0430\u0437\u0430, \u0432 \u0440\u0435\u0437\u0443\u043b\u044c\u0442\u0430\u0442\u0435 \u0447\u0435\u0433\u043e \u043d\u0430\u0448\u0435 \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u0435 \u043f\u043e\u0442\u0435\u0440\u044f\u0435\u0442 \u0441\u0432\u044f\u0437\u044c \u0441 CI-\u0441\u0438\u0441\u0442\u0435\u043c\u043e\u0439, \u0440\u0430\u0441\u0441\u0438\u043d\u0445\u0440\u043e\u043d\u0438\u0437\u0438\u0440\u0443\u0435\u0442\u0441\u044f.<\/p>\n<p>Au\u00dferdem kann bei aufeinanderfolgenden Pushs in einen Branch mit nur kurzem Abstand zwischen ihnen der alte Commit sp\u00e4ter gebaut werden als der neuere: Die alte Version des Images \u00fcberschreibt die neue unter dem Git-Branch-Tag. Solche Probleme kann ein CI\/CD-System l\u00f6sen (zum Beispiel wird in GitLab CI f\u00fcr eine Serie von Commits der letzte Pipeline-Job gestartet). Allerdings unterst\u00fctzen nicht alle Systeme dies, und es sollte einen zuverl\u00e4ssigeren Weg geben, um ein so fundamentales Problem zu verhindern.<\/p>\n<h2>Was ist content-based tagging?<\/h2>\n<p>\nAlso, was ist content-based tagging \u2013 das Tagging von Images basierend auf ihrem Inhalt.<\/p>\n<p>\u0414\u043b\u044f \u0441\u043e\u0437\u0434\u0430\u043d\u0438\u044f Docker-\u0442\u0435\u0433\u043e\u0432 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u044e\u0442\u0441\u044f \u043d\u0435 \u043f\u0440\u0438\u043c\u0438\u0442\u0438\u0432\u044b Git&#8217;\u0430 (Git-\u0432\u0435\u0442\u043a\u0430, Git-\u0442\u0435\u0433\u2026), \u0430 \u043a\u043e\u043d\u0442\u0440\u043e\u043b\u044c\u043d\u0430\u044f \u0441\u0443\u043c\u043c\u0430, \u0441\u0432\u044f\u0437\u0430\u043d\u043d\u0430\u044f \u0441:<\/p>\n<ul>\n<li> <i>dem Inhalt des Images<\/i>. Die Image-Tag-ID spiegelt dessen Inhalt wider. Bei der Erstellung einer neuen Version \u00e4ndert sich diese ID nicht, sofern die Dateien im Image unver\u00e4ndert bleiben.<\/li>\n<li> <i>die Historie dieser Image in Git<\/i>. Images, die mit unterschiedlichen Git-Branches und verschiedenen Erstellungs-Historien \u00fcber werf verbunden sind, werden unterschiedliche Tag-IDs haben.<\/li>\n<\/ul>\n<p>\nAls solche Tag-ID fungiert sozusagen die <b>Signatur der Image-Stufen<\/b>.<\/p>\n<p>Jedes Image besteht aus einer Reihe von Stufen: <code>from<\/code>, <code>before-install<\/code>, <code>git-archive<\/code>, <code>install<\/code>, <code>imports-after-install<\/code>, <code>before-setup<\/code>,\u2026 <code>git-latest-patch<\/code> usw. Jede Stufe hat eine ID, die ihren Inhalt widerspiegelt, \u2014 <b>Stufensignatur<\/b> <i>(stage signature)<\/i>.<\/p>\n<p>Das finale Image, das aus diesen Stufen besteht, wird mit der sogenannten Signatur dieser Stufen getaggt \u2014 <b>Stages signature<\/b>, \u2014 die f\u00fcr alle Stufen des Images eine Zusammenfassung darstellt.<\/p>\n<p>Jedes Image aus der Konfiguration <code>werf.yaml<\/code> wird im Allgemeinen eine eigene solche Signatur und entsprechend einen Docker-Tag haben.<\/p>\n<p>Die Stufensignatur l\u00f6st alle genannten Probleme:<\/p>\n<ul>\n<li> Sie ist resistent gegen leere Git-Commits.<\/li>\n<li> Sie ist resistent gegen Git-Commits, die Dateien ver\u00e4ndern, die f\u00fcr das Image nicht relevant sind.<\/li>\n<li> F\u00fchrt nicht zu Problemen beim \u00dcberschreiben der aktuellen Version des Images beim Neustart von Builds f\u00fcr alte Git-Commits des Branches.<\/li>\n<\/ul>\n<p>\nJetzt ist dies die empfohlene Tagging-Strategie und wird standardm\u00e4\u00dfig in werf f\u00fcr alle CI-Systeme verwendet.<\/p>\n<h2>Wie man es in werf aktiviert und verwendet<\/h2>\n<p>\nDie entsprechende Option ist im Befehl hinzugekommen <code>werf publish<\/code>: <code>--tag-by-stages-signature=true|false<\/code><\/p>\n<p>In CI-Systemen wird die Tagging-Strategie durch den Befehl festgelegt <code>werf ci-env<\/code>. Zuvor wurde daf\u00fcr ein Parameter festgelegt <code>werf ci-env --tagging-strategy=tag-or-branch<\/code>. Jetzt, unabh\u00e4ngig davon, ob diese Option angegeben wird oder nicht, verwendet werf standardm\u00e4\u00dfig die Tagging-Strategie <code>werf ci-env --tagging-strategy=stages-signature<\/code> setzt automatisch die erforderlichen Flags f\u00fcr den Befehl <code>stages-signature<\/code>. Der Befehl <code>werf ci-env<\/code> ), daher m\u00fcssen keine zus\u00e4tzlichen Optionen f\u00fcr diese Befehle angegeben werden. <code>werf build-and-publish<\/code> (oder <code>werf publish<\/code>Zum Beispiel der Befehl:<\/p>\n<p>werf publish --stages-storage :local --images-repo registry.hello.com\/web\/core\/system --tag-by-stages-signature<\/p>\n<pre><code class=\"plaintext\">\u2026 kann folgende Images erstellen:<\/code><\/pre>\n<p>\nregistry.hello.com\/web\/core\/system\/backend:4ef339f84ca22247f01fb335bb19f46c4434014d8daa3d5d6f0e386d<\/p>\n<ul>\n<li> <code>registry.hello.com\/web\/core\/system\/frontend:f44206457e0a4c8a54655543f749799d10a9fe945896dab1c16996c6<\/code><\/li>\n<li> <code>4ef339f84ca22247f01fb335bb19f46c4434014d8daa3d5d6f0e386d<\/code><\/li>\n<\/ul>\n<p>\nHier <code>\u2014 das ist die Sigantur der Stufen des Images<\/code> f44206457e0a4c8a54655543f749799d10a9fe945896dab1c16996c6 <code>backend<\/code>, und <code>\u2014 Sigantur der Stufen des Images<\/code> Bei der Nutzung spezieller Funktionen <code>Frontend<\/code>.<\/p>\n<p>werf_container_image <code>werf_container_env<\/code> und <code>werf_container_env<\/code> In den Helm-Vorlagen sind keine \u00c4nderungen erforderlich: Diese Funktionen generieren automatisch die richtigen Bildnamen.<\/p>\n<p>Beispielkonfiguration im CI-System:<\/p>\n<pre><code class=\"plaintext\">type multiwerf &amp;&amp; source &lt;(multiwerf use 1.1 beta)\ntype werf &amp;&amp; source &lt;(werf ci-env gitlab)\nwerf build-and-publish|deploy<\/code><\/pre>\n<p>\nWeitere Informationen zur Konfiguration finden Sie in der Dokumentation:<\/p>\n<ul>\n<li> <noindex><a rel=\"nofollow\" href=\"https:\/\/ru.werf.io\/v1.1\/documentation\/reference\/publish_process.html#%D1%82%D0%B5%D0%B3%D0%B8%D1%80%D0%BE%D0%B2%D0%B0%D0%BD%D0%B8%D0%B5-%D0%BE%D0%B1%D1%80%D0%B0%D0%B7%D0%BE%D0%B2-%D0%BF%D0%BE-%D1%81%D0%BE%D0%B4%D0%B5%D1%80%D0%B6%D0%B8%D0%BC%D0%BE%D0%BC%D1%83\">Handbuch \u2192 Ver\u00f6ffentlichung (publish)<\/a><\/noindex>;<\/li>\n<li> <noindex><a rel=\"nofollow\" href=\"https:\/\/ru.werf.io\/v1.1\/documentation\/reference\/plugging_into_cicd\/overview.html#stages-signature\">Arbeiten mit CI\/CD \u2192 Allgemeine Informationen \u2192 stages-signature<\/a><\/noindex>;<\/li>\n<li> <noindex><a rel=\"nofollow\" href=\"https:\/\/ru.werf.io\/v1.1\/documentation\/guides\/gitlab_ci_cd_integration.html#gitlab-ciyml\">Integration mit GitLab CI\/CD \u2192 .gitlab-ci.yml<\/a><\/noindex>.<\/li>\n<\/ul>\n<p><\/p>\n<h2>Gesamt<\/h2>\n<p><\/p>\n<ul>\n<li> Neue Option <code>werf publish --tag-by-stages-signature=true|false<\/code>.<\/li>\n<li> Neuer Wert der Option <code>werf ci-env --tagging-strategy=stages-signature|tag-or-branch<\/code> (wenn nicht angegeben, ist standardm\u00e4\u00dfig <code>stages-signature<\/code>).<\/li>\n<li> Wenn zuvor die Tagging-Optionen nach Git-Commits verwendet wurden (<code>WERF_TAG_GIT_COMMIT<\/code> oder die Option <code>werf publish --tag-git-commit COMMIT<\/code>), muss unbedingt auf die Tagging-Strategie umgeschaltet werden. <i>stages-signature<\/i>.<\/li>\n<li> Neue Projekte sollten sofort auf das neue Tagging-Schema umgestellt werden.<\/li>\n<li> Alte Projekte sollten beim Umstieg auf werf 1.1 ebenfalls auf das neue Tagging-Schema umgeschaltet werden, allerdings wird das alte <i>tag-or-branch<\/i> weiterhin unterst\u00fctzt.<\/li>\n<\/ul>\n<p>\nContent-basiertes Tagging l\u00f6st alle in dem Artikel angesprochenen Probleme:<\/p>\n<ul>\n<li> Die Stabilit\u00e4t des Docker-Tag-Namens bei leeren Git-Commits.<\/li>\n<li> Die Stabilit\u00e4t des Docker-Tag-Namens bei Git-Commits, die irrelevante Dateien f\u00fcr das Image \u00e4ndern.<\/li>\n<li> Es f\u00fchrt nicht zu Problemen beim \u00dcberschreiben der aktuellen Version des Images beim Neustart von Builds f\u00fcr alte Git-Commits in Git-Branches.<\/li>\n<\/ul>\n<p>\nNutzen Sie es! Und vergessen Sie nicht, bei uns vorbei zu schauen auf <noindex><a rel=\"nofollow\" href=\"https:\/\/github.com\/flant\/werf\">GitHub<\/a><\/noindex>, um ein Issue zu erstellen oder ein bereits bestehendes zu finden, einen Pluspunkt zu vergeben, einen PR zu erstellen oder einfach die Entwicklung des Projekts zu beobachten.<\/p>\n<h2>P.S.<\/h2>\n<p>\nLesen Sie auch in unserem Blog:<\/p>\n<ul>\n<li> \u00ab<noindex><a rel=\"nofollow\" href=\"https:\/\/habr.com\/ru\/company\/flant\/blog\/493170\/\">Release von Werfer 1.1: Verbesserungen im heutigen Werfer und Pl\u00e4ne f\u00fcr die Zukunft.<\/a><\/noindex>\u00bb<\/li>\n<li> \u00ab<noindex><a rel=\"nofollow\" href=\"https:\/\/habr.com\/ru\/company\/flant\/blog\/481306\/\">Wir freuen uns, werf 1.0 stable vorzustellen: Was hat das mit GitOps, Status und Pl\u00e4nen zu tun?<\/a><\/noindex>\u00bb<\/li>\n<li> \u00ab<noindex><a rel=\"nofollow\" href=\"https:\/\/habr.com\/ru\/company\/flant\/blog\/460351\/\">werf \u2014 unser Tool f\u00fcr CI\/CD in Kubernetes (\u00dcbersicht und Video des Vortrags)<\/a><\/noindex>\u00bb;<\/li>\n<li> Notizen zu den Neuerungen in werf:\n<ul>\n<li> \u00ab<noindex><a rel=\"nofollow\" href=\"https:\/\/habr.com\/ru\/company\/flant\/blog\/476646\/\">3-Wege-Merge im Werfer: Deployment in Kubernetes mit Helm 'auf Steroiden'<\/a><\/noindex>\u00bb;<\/li>\n<li> \u00ab<noindex><a rel=\"nofollow\" href=\"https:\/\/habr.com\/ru\/company\/flant\/blog\/468049\/\">Die Verwendung von werf zur Bereitstellung komplexer Helm-Charts<\/a><\/noindex>\u00bb;<\/li>\n<li> \u00ab<noindex><a rel=\"nofollow\" href=\"https:\/\/habr.com\/ru\/company\/flant\/blog\/465131\/\">Unterst\u00fctzung von Monorepo und Multirepo im Werfer und was Docker Registry damit zu tun hat.<\/a><\/noindex>\u00bb;<\/li>\n<li> \u00ab<noindex><a rel=\"nofollow\" href=\"https:\/\/habr.com\/ru\/company\/flant\/blog\/463613\/\">Docker-Images k\u00f6nnen jetzt auch in werf aus einer normalen Dockerfile gesammelt werden<\/a><\/noindex>\u00bb.<\/li>\n<\/ul>\n<\/li>\n<\/ul>\n<p>Quelle: <a content=\"nofollow\" rel=\"nofollow\" href=\"https:\/\/habr.com\/ru\/company\/flant\/blog\/495112\/\">habr.com<\/a> <\/p>","protected":false,"gt_translate_keys":[{"key":"rendered","format":"html"}]},"excerpt":{"rendered":"<p>werf \u2014 \u043d\u0430\u0448\u0430 GitOps CLI-\u0443\u0442\u0438\u043b\u0438\u0442\u0430 \u0441 \u043e\u0442\u043a\u0440\u044b\u0442\u044b\u043c \u043a\u043e\u0434\u043e\u043c \u0434\u043b\u044f \u0441\u0431\u043e\u0440\u043a\u0438 \u0438 \u0434\u043e\u0441\u0442\u0430\u0432\u043a\u0438 \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u0439 \u0432 Kubernetes. \u0412 \u0440\u0435\u043b\u0438\u0437\u0435 v1.1 \u0431\u044b\u043b\u0430 \u043f\u0440\u0435\u0434\u0441\u0442\u0430\u0432\u043b\u0435\u043d\u0430 \u043d\u043e\u0432\u0430\u044f \u0432\u043e\u0437\u043c\u043e\u0436\u043d\u043e\u0441\u0442\u044c \u0432 \u0441\u0431\u043e\u0440\u0449\u0438\u043a\u0435 \u043e\u0431\u0440\u0430\u0437\u043e\u0432: \u0442\u0435\u0433\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u0435 \u043e\u0431\u0440\u0430\u0437\u043e\u0432 \u043f\u043e \u0441\u043e\u0434\u0435\u0440\u0436\u0438\u043c\u043e\u043c\u0443 \u0438\u043b\u0438 content-based tagging. \u0414\u043e \u0441\u0438\u0445 \u043f\u043e\u0440 \u0442\u0438\u043f\u0438\u0447\u043d\u0430\u044f \u0441\u0445\u0435\u043c\u0430 \u0442\u0435\u0433\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u044f \u0432 werf \u043f\u0440\u0435\u0434\u043f\u043e\u043b\u0430\u0433\u0430\u043b\u0430 \u0442\u0435\u0433\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u0435 Docker-\u043e\u0431\u0440\u0430\u0437\u043e\u0432 \u043f\u043e Git-\u0442\u0435\u0433\u0443, Git-\u0432\u0435\u0442\u043a\u0435 \u0438\u043b\u0438 Git-\u043a\u043e\u043c\u043c\u0438\u0442\u0443. \u041d\u043e \u0443 \u0432\u0441\u0435\u0445 \u044d\u0442\u0438\u0445 \u0441\u0445\u0435\u043c \u0435\u0441\u0442\u044c \u043d\u0435\u0434\u043e\u0441\u0442\u0430\u0442\u043a\u0438, [&hellip;]<\/p>\n","protected":false,"gt_translate_keys":[{"key":"rendered","format":"html"}]},"author":1,"featured_media":76770,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[688],"tags":[],"class_list":["post-76769","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-administrirovanie"],"aioseo_notices":[],"aioseo_head":"\n\t\t<!-- All in One SEO 4.9.10 - aioseo.com -->\n\t<meta name=\"description\" content=\"werf \u2014 \u043d\u0430\u0448\u0430 GitOps CLI-\u0443\u0442\u0438\u043b\u0438\u0442\u0430 \u0441 \u043e\u0442\u043a\u0440\u044b\u0442\u044b\u043c \u043a\u043e\u0434\u043e\u043c \u0434\u043b\u044f \u0441\u0431\u043e\u0440\u043a\u0438 \u0438 \u0434\u043e\u0441\u0442\u0430\u0432\u043a\u0438 \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u0439 \u0432 Kubernetes. \u0412 \u0440\u0435\u043b\u0438\u0437\u0435 v1.1 \u0431\u044b\u043b\u0430 \u043f\u0440\u0435\u0434\u0441\u0442\u0430\u0432\u043b\u0435\u043d\u0430 \u043d\u043e\u0432\u0430\u044f \u0432\u043e\u0437\u043c\u043e\u0436\u043d\u043e\u0441\u0442\u044c \u0432 \u0441\u0431\u043e\u0440\u0449\u0438\u043a\u0435 \u043e\u0431\u0440\u0430\u0437\u043e\u0432: \u0442\u0435\u0433\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u0435 \u043e\u0431\u0440\u0430\u0437\u043e\u0432 \u043f\u043e \u0441\u043e\u0434\u0435\u0440\u0436\u0438\u043c\u043e\u043c\u0443 \u0438\u043b\u0438 content-based tagging. \u0414\u043e \u0441\u0438\u0445 \u043f\u043e\u0440 \u0442\u0438\u043f\u0438\u0447\u043d\u0430\u044f \u0441\u0445\u0435\u043c\u0430 \u0442\u0435\u0433\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u044f \u0432 werf \u043f\u0440\u0435\u0434\u043f\u043e\u043b\u0430\u0433\u0430\u043b\u0430 \u0442\u0435\u0433\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u0435 Docker-\u043e\u0431\u0440\u0430\u0437\u043e\u0432 \u043f\u043e Git-\u0442\u0435\u0433\u0443, Git-\u0432\u0435\u0442\u043a\u0435 \u0438\u043b\u0438 Git-\u043a\u043e\u043c\u043c\u0438\u0442\u0443. \u041d\u043e \u0443 \u0432\u0441\u0435\u0445 \u044d\u0442\u0438\u0445 \u0441\u0445\u0435\u043c \u0435\u0441\u0442\u044c \u043d\u0435\u0434\u043e\u0441\u0442\u0430\u0442\u043a\u0438,\" \/>\n\t<meta name=\"robots\" content=\"max-image-preview:large\" \/>\n\t<meta name=\"author\" content=\"Yuri Gagarin\"\/>\n\t<link rel=\"canonical\" href=\"https:\/\/prohoster.info\/de\/blog\/administrirovanie\/content-based-tagging-v-sborshhike-werf-zachem-i-kak-eto-rabotaet\" \/>\n\t<meta name=\"generator\" content=\"All in One SEO (AIOSEO) 4.9.10\" \/>\n\t\t<meta property=\"og:locale\" content=\"de_DE\" \/>\n\t\t<meta property=\"og:site_name\" content=\"ProHoster | \u041a\u0443\u043f\u0438\u0442\u044c \u043d\u0430\u0434\u0435\u0436\u043d\u044b\u0439 \u0445\u043e\u0441\u0442\u0438\u043d\u0433 \u0434\u043b\u044f \u0441\u0430\u0439\u0442\u043e\u0432 \u0441 \u0437\u0430\u0449\u0438\u0442\u043e\u0439 \u043e\u0442 DDoS, VPS VDS \u0441\u0435\u0440\u0432\u0435\u0440\u044b\" \/>\n\t\t<meta property=\"og:type\" content=\"article\" \/>\n\t\t<meta property=\"og:title\" content=\"\ud83e\udd47Content-based tagging \u0432 \u0441\u0431\u043e\u0440\u0449\u0438\u043a\u0435 werf: \u0437\u0430\u0447\u0435\u043c \u0438 \u043a\u0430\u043a \u044d\u0442\u043e \u0440\u0430\u0431\u043e\u0442\u0430\u0435\u0442? | ProHoster\" \/>\n\t\t<meta property=\"og:description\" content=\"werf \u2014 \u043d\u0430\u0448\u0430 GitOps CLI-\u0443\u0442\u0438\u043b\u0438\u0442\u0430 \u0441 \u043e\u0442\u043a\u0440\u044b\u0442\u044b\u043c \u043a\u043e\u0434\u043e\u043c \u0434\u043b\u044f \u0441\u0431\u043e\u0440\u043a\u0438 \u0438 \u0434\u043e\u0441\u0442\u0430\u0432\u043a\u0438 \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u0439 \u0432 Kubernetes. \u0412 \u0440\u0435\u043b\u0438\u0437\u0435 v1.1 \u0431\u044b\u043b\u0430 \u043f\u0440\u0435\u0434\u0441\u0442\u0430\u0432\u043b\u0435\u043d\u0430 \u043d\u043e\u0432\u0430\u044f \u0432\u043e\u0437\u043c\u043e\u0436\u043d\u043e\u0441\u0442\u044c \u0432 \u0441\u0431\u043e\u0440\u0449\u0438\u043a\u0435 \u043e\u0431\u0440\u0430\u0437\u043e\u0432: \u0442\u0435\u0433\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u0435 \u043e\u0431\u0440\u0430\u0437\u043e\u0432 \u043f\u043e \u0441\u043e\u0434\u0435\u0440\u0436\u0438\u043c\u043e\u043c\u0443 \u0438\u043b\u0438 content-based tagging. \u0414\u043e \u0441\u0438\u0445 \u043f\u043e\u0440 \u0442\u0438\u043f\u0438\u0447\u043d\u0430\u044f \u0441\u0445\u0435\u043c\u0430 \u0442\u0435\u0433\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u044f \u0432 werf \u043f\u0440\u0435\u0434\u043f\u043e\u043b\u0430\u0433\u0430\u043b\u0430 \u0442\u0435\u0433\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u0435 Docker-\u043e\u0431\u0440\u0430\u0437\u043e\u0432 \u043f\u043e Git-\u0442\u0435\u0433\u0443, Git-\u0432\u0435\u0442\u043a\u0435 \u0438\u043b\u0438 Git-\u043a\u043e\u043c\u043c\u0438\u0442\u0443. \u041d\u043e \u0443 \u0432\u0441\u0435\u0445 \u044d\u0442\u0438\u0445 \u0441\u0445\u0435\u043c \u0435\u0441\u0442\u044c \u043d\u0435\u0434\u043e\u0441\u0442\u0430\u0442\u043a\u0438,\" \/>\n\t\t<meta property=\"og:url\" content=\"https:\/\/prohoster.info\/de\/blog\/administrirovanie\/content-based-tagging-v-sborshhike-werf-zachem-i-kak-eto-rabotaet\" \/>\n\t\t<meta property=\"og:image\" content=\"https:\/\/prohoster.info\/wp-content\/uploads\/2021\/11\/logo-350.jpg\" \/>\n\t\t<meta property=\"og:image:secure_url\" content=\"https:\/\/prohoster.info\/wp-content\/uploads\/2021\/11\/logo-350.jpg\" \/>\n\t\t<meta property=\"og:image:width\" content=\"350\" \/>\n\t\t<meta property=\"og:image:height\" content=\"350\" \/>\n\t\t<meta property=\"article:published_time\" content=\"2020-04-04T11:42:27+00:00\" \/>\n\t\t<meta property=\"article:modified_time\" content=\"2020-04-04T11:42:27+00:00\" \/>\n\t\t<meta property=\"article:publisher\" content=\"https:\/\/www.facebook.com\/prohoster\" \/>\n\t\t<meta property=\"article:author\" content=\"https:\/\/www.facebook.com\/prohoster\" \/>\n\t\t<!-- All in One SEO -->\n\n","aioseo_head_json":{"title":"\ud83e\udd47Content-based tagging im werf-Builder: Warum und wie funktioniert das? | ProHoster","description":"werf ist unser Open-Source GitOps CLI-Tool zum Erstellen und Bereitstellen von Anwendungen in Kubernetes. In der Version v1.1 wurde eine neue Funktion im Image-Builder eingef\u00fchrt: die tagbasierte Tagging nach Inhalt oder content-based tagging. Bisher basierte das \u00fcbliche Tagging-Schema in werf auf dem Tagging von Docker-Images nach Git-Tag, Git-Branch oder Git-Commit. Aber alle diese Schemas haben ihre Nachteile,","canonical_url":"https:\/\/prohoster.info\/de\/blog\/administrirovanie\/content-based-tagging-v-sborshhike-werf-zachem-i-kak-eto-rabotaet","robots":"max-image-preview:large","keywords":"","webmasterTools":{"miscellaneous":""},"schema":null,"og:locale":"de_DE","og:site_name":"ProHoster | \u041a\u0443\u043f\u0438\u0442\u044c \u043d\u0430\u0434\u0435\u0436\u043d\u044b\u0439 \u0445\u043e\u0441\u0442\u0438\u043d\u0433 \u0434\u043b\u044f \u0441\u0430\u0439\u0442\u043e\u0432 \u0441 \u0437\u0430\u0449\u0438\u0442\u043e\u0439 \u043e\u0442 DDoS, VPS VDS \u0441\u0435\u0440\u0432\u0435\u0440\u044b","og:type":"article","og:title":"\ud83e\udd47Content-based tagging \u0432 \u0441\u0431\u043e\u0440\u0449\u0438\u043a\u0435 werf: \u0437\u0430\u0447\u0435\u043c \u0438 \u043a\u0430\u043a \u044d\u0442\u043e \u0440\u0430\u0431\u043e\u0442\u0430\u0435\u0442? | ProHoster","og:description":"werf \u2014 \u043d\u0430\u0448\u0430 GitOps CLI-\u0443\u0442\u0438\u043b\u0438\u0442\u0430 \u0441 \u043e\u0442\u043a\u0440\u044b\u0442\u044b\u043c \u043a\u043e\u0434\u043e\u043c \u0434\u043b\u044f \u0441\u0431\u043e\u0440\u043a\u0438 \u0438 \u0434\u043e\u0441\u0442\u0430\u0432\u043a\u0438 \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u0439 \u0432 Kubernetes. \u0412 \u0440\u0435\u043b\u0438\u0437\u0435 v1.1 \u0431\u044b\u043b\u0430 \u043f\u0440\u0435\u0434\u0441\u0442\u0430\u0432\u043b\u0435\u043d\u0430 \u043d\u043e\u0432\u0430\u044f \u0432\u043e\u0437\u043c\u043e\u0436\u043d\u043e\u0441\u0442\u044c \u0432 \u0441\u0431\u043e\u0440\u0449\u0438\u043a\u0435 \u043e\u0431\u0440\u0430\u0437\u043e\u0432: \u0442\u0435\u0433\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u0435 \u043e\u0431\u0440\u0430\u0437\u043e\u0432 \u043f\u043e \u0441\u043e\u0434\u0435\u0440\u0436\u0438\u043c\u043e\u043c\u0443 \u0438\u043b\u0438 content-based tagging. \u0414\u043e \u0441\u0438\u0445 \u043f\u043e\u0440 \u0442\u0438\u043f\u0438\u0447\u043d\u0430\u044f \u0441\u0445\u0435\u043c\u0430 \u0442\u0435\u0433\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u044f \u0432 werf \u043f\u0440\u0435\u0434\u043f\u043e\u043b\u0430\u0433\u0430\u043b\u0430 \u0442\u0435\u0433\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u0435 Docker-\u043e\u0431\u0440\u0430\u0437\u043e\u0432 \u043f\u043e Git-\u0442\u0435\u0433\u0443, Git-\u0432\u0435\u0442\u043a\u0435 \u0438\u043b\u0438 Git-\u043a\u043e\u043c\u043c\u0438\u0442\u0443. \u041d\u043e \u0443 \u0432\u0441\u0435\u0445 \u044d\u0442\u0438\u0445 \u0441\u0445\u0435\u043c \u0435\u0441\u0442\u044c \u043d\u0435\u0434\u043e\u0441\u0442\u0430\u0442\u043a\u0438,","og:url":"https:\/\/prohoster.info\/de\/blog\/administrirovanie\/content-based-tagging-v-sborshhike-werf-zachem-i-kak-eto-rabotaet","og:image":"https:\/\/prohoster.info\/wp-content\/uploads\/2021\/11\/logo-350.jpg","og:image:secure_url":"https:\/\/prohoster.info\/wp-content\/uploads\/2021\/11\/logo-350.jpg","og:image:width":350,"og:image:height":350,"article:published_time":"2020-04-04T11:42:27+00:00","article:modified_time":"2020-04-04T11:42:27+00:00","article:publisher":"https:\/\/www.facebook.com\/prohoster","article:author":"https:\/\/www.facebook.com\/prohoster"},"aioseo_meta_data":{"post_id":"76769","title":null,"description":null,"keywords":null,"keyphrases":null,"primary_term":null,"canonical_url":null,"og_title":null,"og_description":null,"og_object_type":"default","og_image_type":"default","og_image_url":null,"og_image_width":null,"og_image_height":null,"og_image_custom_url":null,"og_image_custom_fields":null,"og_video":null,"og_custom_url":null,"og_article_section":null,"og_article_tags":null,"twitter_use_og":false,"twitter_card":"default","twitter_image_type":"default","twitter_image_url":null,"twitter_image_custom_url":null,"twitter_image_custom_fields":null,"twitter_title":null,"twitter_description":null,"schema":{"blockGraphs":[],"customGraphs":[],"default":{"data":{"Article":[],"Course":[],"Dataset":[],"FAQPage":[],"Movie":[],"Person":[],"Product":[],"ProductReview":[],"Car":[],"Recipe":[],"Service":[],"SoftwareApplication":[],"WebPage":[]},"graphName":"","isEnabled":true},"graphs":[]},"schema_type":null,"schema_type_options":null,"pillar_content":false,"robots_default":true,"robots_noindex":false,"robots_noarchive":false,"robots_nosnippet":false,"robots_nofollow":false,"robots_noimageindex":false,"robots_noodp":false,"robots_notranslate":false,"robots_max_snippet":null,"robots_max_videopreview":null,"robots_max_imagepreview":"large","priority":null,"frequency":null,"local_seo":null,"seo_analyzer_scan_date":null,"breadcrumb_settings":null,"limit_modified_date":false,"reviewed_by":null,"ai":null,"created":"2021-02-28 17:30:22","updated":"2022-09-28 05:59:33"},"gt_translate_keys":[{"key":"link","format":"url"}],"_links":{"self":[{"href":"https:\/\/prohoster.info\/de\/wp-json\/wp\/v2\/posts\/76769","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/prohoster.info\/de\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/prohoster.info\/de\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/prohoster.info\/de\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/prohoster.info\/de\/wp-json\/wp\/v2\/comments?post=76769"}],"version-history":[{"count":0,"href":"https:\/\/prohoster.info\/de\/wp-json\/wp\/v2\/posts\/76769\/revisions"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/prohoster.info\/de\/wp-json\/wp\/v2\/media\/76770"}],"wp:attachment":[{"href":"https:\/\/prohoster.info\/de\/wp-json\/wp\/v2\/media?parent=76769"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/prohoster.info\/de\/wp-json\/wp\/v2\/categories?post=76769"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/prohoster.info\/de\/wp-json\/wp\/v2\/tags?post=76769"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}