mirror of
https://github.com/fluxcd/flagger.git
synced 2026-04-15 06:57:34 +00:00
Publish website
This commit is contained in:
@@ -0,0 +1,106 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en-US">
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<meta name="viewport" content="width=device-width,initial-scale=1">
|
||||
<title>Alerting | Flagger</title>
|
||||
<meta name="description" content="Progressive Delivery operator for Kubernetes (Canary, A/B Testing and Blue/Green deployments)">
|
||||
<link rel="icon" href="/favicon.png">
|
||||
<link rel="stylesheet" href="/website.css">
|
||||
<meta name="keywords" content="gitops kubernetes flagger istio linkerd appmesh contour gloo nginx">
|
||||
<meta name="twitter:card" content="summary_large_image">
|
||||
<meta name="twitter:title" content="Flagger">
|
||||
<meta name="twitter:description" content="Progressive delivery Kubernetes operator (Canary, A/B Testing and Blue/Green deployments)">
|
||||
<meta name="twitter:image:src" content="https://flagger.app/flagger-overview.png">
|
||||
|
||||
<link rel="preload" href="/assets/css/0.styles.a0ada997.css" as="style"><link rel="preload" href="/assets/js/app.b4b27991.js" as="script"><link rel="preload" href="/assets/js/2.ba5bf77c.js" as="script"><link rel="preload" href="/assets/js/30.38bd809e.js" as="script"><link rel="prefetch" href="/assets/js/10.bf6f38d4.js"><link rel="prefetch" href="/assets/js/11.3af38cfe.js"><link rel="prefetch" href="/assets/js/12.eca4b89c.js"><link rel="prefetch" href="/assets/js/13.9104349a.js"><link rel="prefetch" href="/assets/js/14.a4f3d810.js"><link rel="prefetch" href="/assets/js/15.aada2caa.js"><link rel="prefetch" href="/assets/js/16.3012a10b.js"><link rel="prefetch" href="/assets/js/17.a98b6aa9.js"><link rel="prefetch" href="/assets/js/18.e5188926.js"><link rel="prefetch" href="/assets/js/19.bb9498f7.js"><link rel="prefetch" href="/assets/js/20.dce5a04e.js"><link rel="prefetch" href="/assets/js/21.df66561d.js"><link rel="prefetch" href="/assets/js/22.1c5d14b9.js"><link rel="prefetch" href="/assets/js/23.b3dcc355.js"><link rel="prefetch" href="/assets/js/24.4f54d289.js"><link rel="prefetch" href="/assets/js/25.914acd1d.js"><link rel="prefetch" href="/assets/js/26.b2d4f402.js"><link rel="prefetch" href="/assets/js/27.ea9f1f9c.js"><link rel="prefetch" href="/assets/js/28.deae273d.js"><link rel="prefetch" href="/assets/js/29.17c547e6.js"><link rel="prefetch" href="/assets/js/3.8b254d5d.js"><link rel="prefetch" href="/assets/js/31.fbfb336c.js"><link rel="prefetch" href="/assets/js/32.591c3f2b.js"><link rel="prefetch" href="/assets/js/33.c456709f.js"><link rel="prefetch" href="/assets/js/34.5a071e36.js"><link rel="prefetch" href="/assets/js/35.fc27c09e.js"><link rel="prefetch" href="/assets/js/36.144098aa.js"><link rel="prefetch" href="/assets/js/4.26a3069c.js"><link rel="prefetch" href="/assets/js/5.f92a6aca.js"><link rel="prefetch" href="/assets/js/6.ee5ffca3.js"><link rel="prefetch" href="/assets/js/7.6bf27a87.js"><link rel="prefetch" href="/assets/js/8.8b72a8d3.js"><link rel="prefetch" href="/assets/js/9.7919fc1d.js">
|
||||
<link rel="stylesheet" href="/assets/css/0.styles.a0ada997.css">
|
||||
</head>
|
||||
<body>
|
||||
<div id="app" data-server-rendered="true"><div class="theme-container"><header class="navbar"><div class="sidebar-button"><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" role="img" viewBox="0 0 448 512" class="icon"><path fill="currentColor" d="M436 124H12c-6.627 0-12-5.373-12-12V80c0-6.627 5.373-12 12-12h424c6.627 0 12 5.373 12 12v32c0 6.627-5.373 12-12 12zm0 160H12c-6.627 0-12-5.373-12-12v-32c0-6.627 5.373-12 12-12h424c6.627 0 12 5.373 12 12v32c0 6.627-5.373 12-12 12zm0 160H12c-6.627 0-12-5.373-12-12v-32c0-6.627 5.373-12 12-12h424c6.627 0 12 5.373 12 12v32c0 6.627-5.373 12-12 12z"></path></svg></div> <a href="/" class="home-link router-link-active"><!----> <span class="site-name">Flagger</span></a> <div class="links"><div class="search-box"><input aria-label="Search" autocomplete="off" spellcheck="false" value=""> <!----></div> <nav class="nav-links can-hide"><div class="nav-item"><a href="https://docs.flagger.app" target="_blank" rel="noopener noreferrer" class="nav-link external">
|
||||
Docs
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></div><div class="nav-item"><a href="https://github.com/weaveworks/flagger/blob/master/CHANGELOG.md" target="_blank" rel="noopener noreferrer" class="nav-link external">
|
||||
Changelog
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></div> <a href="https://github.com/weaveworks/flagger" target="_blank" rel="noopener noreferrer" class="repo-link">
|
||||
GitHub
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></nav></div></header> <div class="sidebar-mask"></div> <aside class="sidebar"><nav class="nav-links"><div class="nav-item"><a href="https://docs.flagger.app" target="_blank" rel="noopener noreferrer" class="nav-link external">
|
||||
Docs
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></div><div class="nav-item"><a href="https://github.com/weaveworks/flagger/blob/master/CHANGELOG.md" target="_blank" rel="noopener noreferrer" class="nav-link external">
|
||||
Changelog
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></div> <a href="https://github.com/weaveworks/flagger" target="_blank" rel="noopener noreferrer" class="repo-link">
|
||||
GitHub
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></nav> <ul class="sidebar-links"><li><a href="/" class="sidebar-link">Home</a></li><li><section class="sidebar-group depth-0"><a href="/intro/" class="sidebar-heading clickable"><span>Introduction</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/intro/" class="sidebar-link">Get Started</a></li><li><a href="/intro/faq.html" class="sidebar-link">FAQ</a></li></ul></section></li><li><section class="sidebar-group depth-0"><a href="/install/flagger-install-on-kubernetes" class="sidebar-heading clickable"><span>Install</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/install/flagger-install-on-kubernetes.html" class="sidebar-link">On Kubernetes</a></li><li><a href="/install/flagger-install-on-google-cloud.html" class="sidebar-link">On GKE Istio</a></li><li><a href="/install/flagger-install-on-eks-appmesh.html" class="sidebar-link">On EKS App Mesh</a></li></ul></section></li><li><section class="sidebar-group depth-0"><a href="/usage/how-it-works" class="sidebar-heading clickable open"><span>Usage</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/usage/how-it-works.html" class="sidebar-link">How it works</a></li><li><a href="/usage/deployment-strategies.html" class="sidebar-link">Deployment Strategies</a></li><li><a href="/usage/metrics.html" class="sidebar-link">Metrics Analysis</a></li><li><a href="/usage/webhooks.html" class="sidebar-link">Webhooks</a></li><li><a href="/usage/alerting.html" class="active sidebar-link">Alerting</a><ul class="sidebar-sub-headers"><li class="sidebar-sub-header"><a href="/usage/alerting.html#global-configuration" class="sidebar-link">Global configuration</a></li><li class="sidebar-sub-header"><a href="/usage/alerting.html#canary-configuration" class="sidebar-link">Canary configuration</a></li><li class="sidebar-sub-header"><a href="/usage/alerting.html#prometheus-alert-manager" class="sidebar-link">Prometheus Alert Manager</a></li></ul></li><li><a href="/usage/monitoring.html" class="sidebar-link">Monitoring</a></li></ul></section></li><li><section class="sidebar-group depth-0"><a href="/tutorials/istio-progressive-delivery" class="sidebar-heading clickable"><span>Tutorials</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/tutorials/istio-progressive-delivery.html" class="sidebar-link">Istio Canaries</a></li><li><a href="/tutorials/istio-ab-testing.html" class="sidebar-link">Istio A/B Testing</a></li><li><a href="/tutorials/linkerd-progressive-delivery.html" class="sidebar-link">Linkerd Canaries</a></li><li><a href="/tutorials/appmesh-progressive-delivery.html" class="sidebar-link">App Mesh Canaries</a></li><li><a href="/tutorials/nginx-progressive-delivery.html" class="sidebar-link">NGINX Ingress Canaries</a></li><li><a href="/tutorials/gloo-progressive-delivery.html" class="sidebar-link">Gloo Canaries</a></li><li><a href="/tutorials/contour-progressive-delivery.html" class="sidebar-link">Contour Canaries</a></li><li><a href="/tutorials/kubernetes-blue-green.html" class="sidebar-link">Kubernetes Blue/Green</a></li><li><a href="/tutorials/canary-helm-gitops.html" class="sidebar-link">Canaries with Helm charts and GitOps</a></li></ul></section></li><li><section class="sidebar-group depth-0"><a href="/dev/dev-guide" class="sidebar-heading clickable"><span>Dev</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/dev/dev-guide.html" class="sidebar-link">Development Guide</a></li><li><a href="/dev/release-guide.html" class="sidebar-link">Release Guide</a></li><li><a href="/dev/upgrade-guide.html" class="sidebar-link">Upgrade Guide</a></li></ul></section></li></ul> </aside> <main class="page"> <div class="theme-default-content content__default"><h1 id="alerting"><a href="#alerting" aria-hidden="true" class="header-anchor">#</a> Alerting</h1> <p>Flagger can be configured to send alerts to various chat platforms. You can define a global alert provider at
|
||||
install time or configure alerts on a per canary basis.</p> <h2 id="global-configuration"><a href="#global-configuration" aria-hidden="true" class="header-anchor">#</a> Global configuration</h2> <p>Flagger can be configured to send Slack notifications:</p> <div class="language-bash extra-class"><pre class="language-bash"><code>helm upgrade -i flagger flagger/flagger <span class="token punctuation">\</span>
|
||||
--set slack.url<span class="token operator">=</span>https://hooks.slack.com/services/YOUR/SLACK/WEBHOOK <span class="token punctuation">\</span>
|
||||
--set slack.channel<span class="token operator">=</span>general <span class="token punctuation">\</span>
|
||||
--set slack.user<span class="token operator">=</span>flagger
|
||||
</code></pre></div><p>Once configured with a Slack incoming <strong>webhook</strong>, Flagger will post messages when a canary deployment
|
||||
has been initialised, when a new revision has been detected and if the canary analysis failed or succeeded.</p> <p><img src="https://raw.githubusercontent.com/weaveworks/flagger/master/docs/screens/slack-canary-notifications.png" alt="Slack Notifications"></p> <p>A canary deployment will be rolled back if the progress deadline exceeded or if the analysis reached the
|
||||
maximum number of failed checks:</p> <p><img src="https://raw.githubusercontent.com/weaveworks/flagger/master/docs/screens/slack-canary-failed.png" alt="Slack Notifications"></p> <p>Flagger can be configured to send notifications to Microsoft Teams:</p> <div class="language-bash extra-class"><pre class="language-bash"><code>helm upgrade -i flagger flagger/flagger <span class="token punctuation">\</span>
|
||||
--set msteams.url<span class="token operator">=</span>https://outlook.office.com/webhook/YOUR/TEAMS/WEBHOOK
|
||||
</code></pre></div><p>Similar to Slack, Flagger alerts on canary analysis events:</p> <p><img src="https://raw.githubusercontent.com/weaveworks/flagger/master/docs/screens/flagger-ms-teams-notifications.png" alt="MS Teams Notifications"></p> <p><img src="https://raw.githubusercontent.com/weaveworks/flagger/master/docs/screens/flagger-ms-teams-failed.png" alt="MS Teams Notifications"></p> <h2 id="canary-configuration"><a href="#canary-configuration" aria-hidden="true" class="header-anchor">#</a> Canary configuration</h2> <p>Configuring alerting globally has several limitations as it's not possible to specify different channels
|
||||
or configure the verbosity on a per canary basis.
|
||||
To make the alerting move flexible, the canary analysis can be extended
|
||||
with a list of alerts that reference an alert provider.
|
||||
For each alert, users can configure the severity level.
|
||||
The alerts section overrides the global setting.</p> <p>Slack example:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code><span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> flagger.app/v1beta1
|
||||
<span class="token key atrule">kind</span><span class="token punctuation">:</span> AlertProvider
|
||||
<span class="token key atrule">metadata</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">name</span><span class="token punctuation">:</span> on<span class="token punctuation">-</span>call
|
||||
<span class="token key atrule">namespace</span><span class="token punctuation">:</span> flagger
|
||||
<span class="token key atrule">spec</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> slack
|
||||
<span class="token key atrule">channel</span><span class="token punctuation">:</span> on<span class="token punctuation">-</span>call<span class="token punctuation">-</span>alerts
|
||||
<span class="token key atrule">username</span><span class="token punctuation">:</span> flagger
|
||||
<span class="token comment"># webhook address (ignored if secretRef is specified)</span>
|
||||
<span class="token key atrule">address</span><span class="token punctuation">:</span> https<span class="token punctuation">:</span>//hooks.slack.com/services/YOUR/SLACK/WEBHOOK
|
||||
<span class="token comment"># secret containing the webhook address (optional)</span>
|
||||
<span class="token key atrule">secretRef</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">name</span><span class="token punctuation">:</span> on<span class="token punctuation">-</span>call<span class="token punctuation">-</span>url
|
||||
<span class="token punctuation">---</span>
|
||||
<span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> v1
|
||||
<span class="token key atrule">kind</span><span class="token punctuation">:</span> Secret
|
||||
<span class="token key atrule">metadata</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">name</span><span class="token punctuation">:</span> on<span class="token punctuation">-</span>call<span class="token punctuation">-</span>url
|
||||
<span class="token key atrule">namespace</span><span class="token punctuation">:</span> flagger
|
||||
<span class="token key atrule">data</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">address</span><span class="token punctuation">:</span> <encoded<span class="token punctuation">-</span>url<span class="token punctuation">></span>
|
||||
</code></pre></div><p>The alert provider <strong>type</strong> can be: <code>slack</code>, <code>msteams</code>, <code>rocket</code> or <code>discord</code>. When set to <code>discord</code>,
|
||||
Flagger will use <a href="https://birdie0.github.io/discord-webhooks-guide/other/slack_formatting.html" target="_blank" rel="noopener noreferrer">Slack formatting<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a>
|
||||
and will append <code>/slack</code> to the Discord address.</p> <p>When not specified, <strong>channel</strong> defaults to <code>general</code> and <strong>username</strong> defaults to <code>flagger</code>.</p> <p>When <strong>secretRef</strong> is specified, the Kubernetes secret must contain a data field named <code>address</code>,
|
||||
the address in the secret will take precedence over the <strong>address</strong> field in the provider spec.</p> <p>The canary analysis can have a list of alerts, each alert referencing an alert provider:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code> <span class="token key atrule">analysis</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">alerts</span><span class="token punctuation">:</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> <span class="token string">"on-call Slack"</span>
|
||||
<span class="token key atrule">severity</span><span class="token punctuation">:</span> error
|
||||
<span class="token key atrule">providerRef</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">name</span><span class="token punctuation">:</span> on<span class="token punctuation">-</span>call
|
||||
<span class="token key atrule">namespace</span><span class="token punctuation">:</span> flagger
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> <span class="token string">"qa Discord"</span>
|
||||
<span class="token key atrule">severity</span><span class="token punctuation">:</span> warn
|
||||
<span class="token key atrule">providerRef</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">name</span><span class="token punctuation">:</span> qa<span class="token punctuation">-</span>discord
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> <span class="token string">"dev MS Teams"</span>
|
||||
<span class="token key atrule">severity</span><span class="token punctuation">:</span> info
|
||||
<span class="token key atrule">providerRef</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">name</span><span class="token punctuation">:</span> dev<span class="token punctuation">-</span>msteams
|
||||
</code></pre></div><p>Alert fields:</p> <ul><li><strong>name</strong> (required)</li> <li><strong>severity</strong> levels: <code>info</code>, <code>warn</code>, <code>error</code> (default info)</li> <li><strong>providerRef.name</strong> alert provider name (required)</li> <li><strong>providerRef.namespace</strong> alert provider namespace (defaults to the canary namespace)</li></ul> <p>When the severity is set to <code>warn</code>, Flagger will alert when waiting on manual confirmation or if the analysis fails.
|
||||
When the severity is set to <code>error</code>, Flagger will alert only if the canary analysis fails.</p> <h2 id="prometheus-alert-manager"><a href="#prometheus-alert-manager" aria-hidden="true" class="header-anchor">#</a> Prometheus Alert Manager</h2> <p>You can use Alertmanager to trigger alerts when a canary deployment failed:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code> <span class="token punctuation">-</span> <span class="token key atrule">alert</span><span class="token punctuation">:</span> canary_rollback
|
||||
<span class="token key atrule">expr</span><span class="token punctuation">:</span> flagger_canary_status <span class="token punctuation">></span> 1
|
||||
<span class="token key atrule">for</span><span class="token punctuation">:</span> 1m
|
||||
<span class="token key atrule">labels</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">severity</span><span class="token punctuation">:</span> warning
|
||||
<span class="token key atrule">annotations</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">summary</span><span class="token punctuation">:</span> <span class="token string">"Canary failed"</span>
|
||||
<span class="token key atrule">description</span><span class="token punctuation">:</span> <span class="token string">"Workload {{ $labels.name }} namespace {{ $labels.namespace }}"</span>
|
||||
</code></pre></div></div> <footer class="page-edit"><!----> <!----></footer> <div class="page-nav"><p class="inner"><span class="prev">
|
||||
←
|
||||
<a href="/usage/webhooks.html" class="prev">
|
||||
Webhooks
|
||||
</a></span> <span class="next"><a href="/usage/monitoring.html">
|
||||
Monitoring
|
||||
</a>
|
||||
→
|
||||
</span></p></div> </main></div><div class="global-ui"></div></div>
|
||||
<script src="/assets/js/app.b4b27991.js" defer></script><script src="/assets/js/2.ba5bf77c.js" defer></script><script src="/assets/js/30.38bd809e.js" defer></script>
|
||||
</body>
|
||||
</html>
|
||||
@@ -0,0 +1,160 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en-US">
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<meta name="viewport" content="width=device-width,initial-scale=1">
|
||||
<title>Deployment Strategies | Flagger</title>
|
||||
<meta name="description" content="Progressive Delivery operator for Kubernetes (Canary, A/B Testing and Blue/Green deployments)">
|
||||
<link rel="icon" href="/favicon.png">
|
||||
<link rel="stylesheet" href="/website.css">
|
||||
<meta name="keywords" content="gitops kubernetes flagger istio linkerd appmesh contour gloo nginx">
|
||||
<meta name="twitter:card" content="summary_large_image">
|
||||
<meta name="twitter:title" content="Flagger">
|
||||
<meta name="twitter:description" content="Progressive delivery Kubernetes operator (Canary, A/B Testing and Blue/Green deployments)">
|
||||
<meta name="twitter:image:src" content="https://flagger.app/flagger-overview.png">
|
||||
|
||||
<link rel="preload" href="/assets/css/0.styles.a0ada997.css" as="style"><link rel="preload" href="/assets/js/app.b4b27991.js" as="script"><link rel="preload" href="/assets/js/2.ba5bf77c.js" as="script"><link rel="preload" href="/assets/js/31.fbfb336c.js" as="script"><link rel="prefetch" href="/assets/js/10.bf6f38d4.js"><link rel="prefetch" href="/assets/js/11.3af38cfe.js"><link rel="prefetch" href="/assets/js/12.eca4b89c.js"><link rel="prefetch" href="/assets/js/13.9104349a.js"><link rel="prefetch" href="/assets/js/14.a4f3d810.js"><link rel="prefetch" href="/assets/js/15.aada2caa.js"><link rel="prefetch" href="/assets/js/16.3012a10b.js"><link rel="prefetch" href="/assets/js/17.a98b6aa9.js"><link rel="prefetch" href="/assets/js/18.e5188926.js"><link rel="prefetch" href="/assets/js/19.bb9498f7.js"><link rel="prefetch" href="/assets/js/20.dce5a04e.js"><link rel="prefetch" href="/assets/js/21.df66561d.js"><link rel="prefetch" href="/assets/js/22.1c5d14b9.js"><link rel="prefetch" href="/assets/js/23.b3dcc355.js"><link rel="prefetch" href="/assets/js/24.4f54d289.js"><link rel="prefetch" href="/assets/js/25.914acd1d.js"><link rel="prefetch" href="/assets/js/26.b2d4f402.js"><link rel="prefetch" href="/assets/js/27.ea9f1f9c.js"><link rel="prefetch" href="/assets/js/28.deae273d.js"><link rel="prefetch" href="/assets/js/29.17c547e6.js"><link rel="prefetch" href="/assets/js/3.8b254d5d.js"><link rel="prefetch" href="/assets/js/30.38bd809e.js"><link rel="prefetch" href="/assets/js/32.591c3f2b.js"><link rel="prefetch" href="/assets/js/33.c456709f.js"><link rel="prefetch" href="/assets/js/34.5a071e36.js"><link rel="prefetch" href="/assets/js/35.fc27c09e.js"><link rel="prefetch" href="/assets/js/36.144098aa.js"><link rel="prefetch" href="/assets/js/4.26a3069c.js"><link rel="prefetch" href="/assets/js/5.f92a6aca.js"><link rel="prefetch" href="/assets/js/6.ee5ffca3.js"><link rel="prefetch" href="/assets/js/7.6bf27a87.js"><link rel="prefetch" href="/assets/js/8.8b72a8d3.js"><link rel="prefetch" href="/assets/js/9.7919fc1d.js">
|
||||
<link rel="stylesheet" href="/assets/css/0.styles.a0ada997.css">
|
||||
</head>
|
||||
<body>
|
||||
<div id="app" data-server-rendered="true"><div class="theme-container"><header class="navbar"><div class="sidebar-button"><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" role="img" viewBox="0 0 448 512" class="icon"><path fill="currentColor" d="M436 124H12c-6.627 0-12-5.373-12-12V80c0-6.627 5.373-12 12-12h424c6.627 0 12 5.373 12 12v32c0 6.627-5.373 12-12 12zm0 160H12c-6.627 0-12-5.373-12-12v-32c0-6.627 5.373-12 12-12h424c6.627 0 12 5.373 12 12v32c0 6.627-5.373 12-12 12zm0 160H12c-6.627 0-12-5.373-12-12v-32c0-6.627 5.373-12 12-12h424c6.627 0 12 5.373 12 12v32c0 6.627-5.373 12-12 12z"></path></svg></div> <a href="/" class="home-link router-link-active"><!----> <span class="site-name">Flagger</span></a> <div class="links"><div class="search-box"><input aria-label="Search" autocomplete="off" spellcheck="false" value=""> <!----></div> <nav class="nav-links can-hide"><div class="nav-item"><a href="https://docs.flagger.app" target="_blank" rel="noopener noreferrer" class="nav-link external">
|
||||
Docs
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></div><div class="nav-item"><a href="https://github.com/weaveworks/flagger/blob/master/CHANGELOG.md" target="_blank" rel="noopener noreferrer" class="nav-link external">
|
||||
Changelog
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></div> <a href="https://github.com/weaveworks/flagger" target="_blank" rel="noopener noreferrer" class="repo-link">
|
||||
GitHub
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></nav></div></header> <div class="sidebar-mask"></div> <aside class="sidebar"><nav class="nav-links"><div class="nav-item"><a href="https://docs.flagger.app" target="_blank" rel="noopener noreferrer" class="nav-link external">
|
||||
Docs
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></div><div class="nav-item"><a href="https://github.com/weaveworks/flagger/blob/master/CHANGELOG.md" target="_blank" rel="noopener noreferrer" class="nav-link external">
|
||||
Changelog
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></div> <a href="https://github.com/weaveworks/flagger" target="_blank" rel="noopener noreferrer" class="repo-link">
|
||||
GitHub
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></nav> <ul class="sidebar-links"><li><a href="/" class="sidebar-link">Home</a></li><li><section class="sidebar-group depth-0"><a href="/intro/" class="sidebar-heading clickable"><span>Introduction</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/intro/" class="sidebar-link">Get Started</a></li><li><a href="/intro/faq.html" class="sidebar-link">FAQ</a></li></ul></section></li><li><section class="sidebar-group depth-0"><a href="/install/flagger-install-on-kubernetes" class="sidebar-heading clickable"><span>Install</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/install/flagger-install-on-kubernetes.html" class="sidebar-link">On Kubernetes</a></li><li><a href="/install/flagger-install-on-google-cloud.html" class="sidebar-link">On GKE Istio</a></li><li><a href="/install/flagger-install-on-eks-appmesh.html" class="sidebar-link">On EKS App Mesh</a></li></ul></section></li><li><section class="sidebar-group depth-0"><a href="/usage/how-it-works" class="sidebar-heading clickable open"><span>Usage</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/usage/how-it-works.html" class="sidebar-link">How it works</a></li><li><a href="/usage/deployment-strategies.html" class="active sidebar-link">Deployment Strategies</a><ul class="sidebar-sub-headers"><li class="sidebar-sub-header"><a href="/usage/deployment-strategies.html#canary-release" class="sidebar-link">Canary Release</a></li><li class="sidebar-sub-header"><a href="/usage/deployment-strategies.html#a-b-testing" class="sidebar-link">A/B Testing</a></li><li class="sidebar-sub-header"><a href="/usage/deployment-strategies.html#blue-green-deployments" class="sidebar-link">Blue/Green Deployments</a></li><li class="sidebar-sub-header"><a href="/usage/deployment-strategies.html#blue-green-with-traffic-mirroring" class="sidebar-link">Blue/Green with Traffic Mirroring</a></li></ul></li><li><a href="/usage/metrics.html" class="sidebar-link">Metrics Analysis</a></li><li><a href="/usage/webhooks.html" class="sidebar-link">Webhooks</a></li><li><a href="/usage/alerting.html" class="sidebar-link">Alerting</a></li><li><a href="/usage/monitoring.html" class="sidebar-link">Monitoring</a></li></ul></section></li><li><section class="sidebar-group depth-0"><a href="/tutorials/istio-progressive-delivery" class="sidebar-heading clickable"><span>Tutorials</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/tutorials/istio-progressive-delivery.html" class="sidebar-link">Istio Canaries</a></li><li><a href="/tutorials/istio-ab-testing.html" class="sidebar-link">Istio A/B Testing</a></li><li><a href="/tutorials/linkerd-progressive-delivery.html" class="sidebar-link">Linkerd Canaries</a></li><li><a href="/tutorials/appmesh-progressive-delivery.html" class="sidebar-link">App Mesh Canaries</a></li><li><a href="/tutorials/nginx-progressive-delivery.html" class="sidebar-link">NGINX Ingress Canaries</a></li><li><a href="/tutorials/gloo-progressive-delivery.html" class="sidebar-link">Gloo Canaries</a></li><li><a href="/tutorials/contour-progressive-delivery.html" class="sidebar-link">Contour Canaries</a></li><li><a href="/tutorials/kubernetes-blue-green.html" class="sidebar-link">Kubernetes Blue/Green</a></li><li><a href="/tutorials/canary-helm-gitops.html" class="sidebar-link">Canaries with Helm charts and GitOps</a></li></ul></section></li><li><section class="sidebar-group depth-0"><a href="/dev/dev-guide" class="sidebar-heading clickable"><span>Dev</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/dev/dev-guide.html" class="sidebar-link">Development Guide</a></li><li><a href="/dev/release-guide.html" class="sidebar-link">Release Guide</a></li><li><a href="/dev/upgrade-guide.html" class="sidebar-link">Upgrade Guide</a></li></ul></section></li></ul> </aside> <main class="page"> <div class="theme-default-content content__default"><h1 id="deployment-strategies"><a href="#deployment-strategies" aria-hidden="true" class="header-anchor">#</a> Deployment Strategies</h1> <p>Flagger can run automated application analysis, promotion and rollback for the following deployment strategies:</p> <ul><li><strong>Canary Release</strong> (progressive traffic shifting)
|
||||
<ul><li>Istio, Linkerd, App Mesh, NGINX, Contour, Gloo</li></ul></li> <li><strong>A/B Testing</strong> (HTTP headers and cookies traffic routing)
|
||||
<ul><li>Istio, App Mesh, NGINX, Contour</li></ul></li> <li><strong>Blue/Green</strong> (traffic switching)
|
||||
<ul><li>Kubernetes CNI, Istio, Linkerd, App Mesh, NGINX, Contour, Gloo</li></ul></li> <li><strong>Blue/Green Mirroring</strong> (traffic shadowing)
|
||||
<ul><li>Istio</li></ul></li></ul> <p>For Canary releases and A/B testing you'll need a Layer 7 traffic management solution like a service mesh or an ingress controller.
|
||||
For Blue/Green deployments no service mesh or ingress controller is required.</p> <p>A canary analysis is triggered by changes in any of the following objects:</p> <ul><li>Deployment PodSpec (container image, command, ports, env, resources, etc)</li> <li>ConfigMaps mounted as volumes or mapped to environment variables</li> <li>Secrets mounted as volumes or mapped to environment variables</li></ul> <h2 id="canary-release"><a href="#canary-release" aria-hidden="true" class="header-anchor">#</a> Canary Release</h2> <p>Flagger implements a control loop that gradually shifts traffic to the canary while measuring key performance
|
||||
indicators like HTTP requests success rate, requests average duration and pod health.
|
||||
Based on analysis of the KPIs a canary is promoted or aborted.</p> <p><img src="https://raw.githubusercontent.com/weaveworks/flagger/master/docs/diagrams/flagger-canary-steps.png" alt="Flagger Canary Stages"></p> <p>The canary analysis runs periodically until it reaches the maximum traffic weight or the failed checks threshold.</p> <p>Spec:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code> <span class="token key atrule">analysis</span><span class="token punctuation">:</span>
|
||||
<span class="token comment"># schedule interval (default 60s)</span>
|
||||
<span class="token key atrule">interval</span><span class="token punctuation">:</span> 1m
|
||||
<span class="token comment"># max number of failed metric checks before rollback</span>
|
||||
<span class="token key atrule">threshold</span><span class="token punctuation">:</span> <span class="token number">10</span>
|
||||
<span class="token comment"># max traffic percentage routed to canary</span>
|
||||
<span class="token comment"># percentage (0-100)</span>
|
||||
<span class="token key atrule">maxWeight</span><span class="token punctuation">:</span> <span class="token number">50</span>
|
||||
<span class="token comment"># canary increment step</span>
|
||||
<span class="token comment"># percentage (0-100)</span>
|
||||
<span class="token key atrule">stepWeight</span><span class="token punctuation">:</span> <span class="token number">2</span>
|
||||
<span class="token comment"># deploy straight to production without</span>
|
||||
<span class="token comment"># the metrics and webhook checks</span>
|
||||
<span class="token key atrule">skipAnalysis</span><span class="token punctuation">:</span> <span class="token boolean important">false</span>
|
||||
</code></pre></div><p>The above analysis, if it succeeds, will run for 25 minutes while validating the HTTP metrics and webhooks every minute.
|
||||
You can determine the minimum time that it takes to validate and promote a canary deployment using this formula:</p> <div class="language- extra-class"><pre class="language-text"><code>interval * (maxWeight / stepWeight)
|
||||
</code></pre></div><p>And the time it takes for a canary to be rollback when the metrics or webhook checks are failing:</p> <div class="language- extra-class"><pre class="language-text"><code>interval * threshold
|
||||
</code></pre></div><p>In emergency cases, you may want to skip the analysis phase and ship changes directly to production.
|
||||
At any time you can set the <code>spec.skipAnalysis: true</code>.
|
||||
When skip analysis is enabled, Flagger checks if the canary deployment is healthy and
|
||||
promotes it without analysing it. If an analysis is underway, Flagger cancels it and runs the promotion.</p> <p>Gated canary promotion stages:</p> <ul><li>scan for canary deployments</li> <li>check primary and canary deployment status
|
||||
<ul><li>halt advancement if a rolling update is underway</li> <li>halt advancement if pods are unhealthy</li></ul></li> <li>call confirm-rollout webhooks and check results
|
||||
<ul><li>halt advancement if any hook returns a non HTTP 2xx result</li></ul></li> <li>call pre-rollout webhooks and check results
|
||||
<ul><li>halt advancement if any hook returns a non HTTP 2xx result</li> <li>increment the failed checks counter</li></ul></li> <li>increase canary traffic weight percentage from 0% to 2% (step weight)</li> <li>call rollout webhooks and check results</li> <li>check canary HTTP request success rate and latency
|
||||
<ul><li>halt advancement if any metric is under the specified threshold</li> <li>increment the failed checks counter</li></ul></li> <li>check if the number of failed checks reached the threshold
|
||||
<ul><li>route all traffic to primary</li> <li>scale to zero the canary deployment and mark it as failed</li> <li>call post-rollout webhooks</li> <li>post the analysis result to Slack</li> <li>wait for the canary deployment to be updated and start over</li></ul></li> <li>increase canary traffic weight by 2% (step weight) till it reaches 50% (max weight)
|
||||
<ul><li>halt advancement if any webhook call fails</li> <li>halt advancement while canary request success rate is under the threshold</li> <li>halt advancement while canary request duration P99 is over the threshold</li> <li>halt advancement while any custom metric check fails</li> <li>halt advancement if the primary or canary deployment becomes unhealthy</li> <li>halt advancement while canary deployment is being scaled up/down by HPA</li></ul></li> <li>call confirm-promotion webhooks and check results
|
||||
<ul><li>halt advancement if any hook returns a non HTTP 2xx result</li></ul></li> <li>promote canary to primary
|
||||
<ul><li>copy ConfigMaps and Secrets from canary to primary</li> <li>copy canary deployment spec template over primary</li></ul></li> <li>wait for primary rolling update to finish
|
||||
<ul><li>halt advancement if pods are unhealthy</li></ul></li> <li>route all traffic to primary</li> <li>scale to zero the canary deployment</li> <li>mark rollout as finished</li> <li>call post-rollout webhooks</li> <li>send notification with the canary analysis result</li> <li>wait for the canary deployment to be updated and start over</li></ul> <h2 id="a-b-testing"><a href="#a-b-testing" aria-hidden="true" class="header-anchor">#</a> A/B Testing</h2> <p>For frontend applications that require session affinity you should use HTTP headers or cookies match conditions
|
||||
to ensure a set of users will stay on the same version for the whole duration of the canary analysis.</p> <p><img src="https://raw.githubusercontent.com/weaveworks/flagger/master/docs/diagrams/flagger-abtest-steps.png" alt="Flagger A/B Testing Stages"></p> <p>You can enable A/B testing by specifying the HTTP match conditions and the number of iterations.
|
||||
If Flagger finds a HTTP match condition, it will ignore the <code>maxWeight</code> and <code>stepWeight</code> settings.</p> <p>Istio example:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code> <span class="token key atrule">analysis</span><span class="token punctuation">:</span>
|
||||
<span class="token comment"># schedule interval (default 60s)</span>
|
||||
<span class="token key atrule">interval</span><span class="token punctuation">:</span> 1m
|
||||
<span class="token comment"># total number of iterations</span>
|
||||
<span class="token key atrule">iterations</span><span class="token punctuation">:</span> <span class="token number">10</span>
|
||||
<span class="token comment"># max number of failed iterations before rollback</span>
|
||||
<span class="token key atrule">threshold</span><span class="token punctuation">:</span> <span class="token number">2</span>
|
||||
<span class="token comment"># canary match condition</span>
|
||||
<span class="token key atrule">match</span><span class="token punctuation">:</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">headers</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">x-canary</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">regex</span><span class="token punctuation">:</span> <span class="token string">".*insider.*"</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">headers</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">cookie</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">regex</span><span class="token punctuation">:</span> <span class="token string">"^(.*?;)?(canary=always)(;.*)?$"</span>
|
||||
</code></pre></div><p>The above configuration will run an analysis for ten minutes targeting the Safari users and those that have a test cookie.
|
||||
You can determine the minimum time that it takes to validate and promote a canary deployment using this formula:</p> <div class="language- extra-class"><pre class="language-text"><code>interval * iterations
|
||||
</code></pre></div><p>And the time it takes for a canary to be rollback when the metrics or webhook checks are failing:</p> <div class="language- extra-class"><pre class="language-text"><code>interval * threshold
|
||||
</code></pre></div><p>App Mesh example:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code> <span class="token key atrule">analysis</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">interval</span><span class="token punctuation">:</span> 1m
|
||||
<span class="token key atrule">threshold</span><span class="token punctuation">:</span> <span class="token number">10</span>
|
||||
<span class="token key atrule">iterations</span><span class="token punctuation">:</span> <span class="token number">2</span>
|
||||
<span class="token key atrule">match</span><span class="token punctuation">:</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">headers</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">user-agent</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">regex</span><span class="token punctuation">:</span> <span class="token string">".*Chrome.*"</span>
|
||||
</code></pre></div><p>Note that App Mesh supports a single condition.</p> <p>Contour example:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code> <span class="token key atrule">analysis</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">interval</span><span class="token punctuation">:</span> 1m
|
||||
<span class="token key atrule">threshold</span><span class="token punctuation">:</span> <span class="token number">10</span>
|
||||
<span class="token key atrule">iterations</span><span class="token punctuation">:</span> <span class="token number">2</span>
|
||||
<span class="token key atrule">match</span><span class="token punctuation">:</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">headers</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">user-agent</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">prefix</span><span class="token punctuation">:</span> <span class="token string">"Chrome"</span>
|
||||
</code></pre></div><p>Note that Contour does not support regex, you can use prefix, suffix or exact.</p> <p>NGINX example:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code> <span class="token key atrule">analysis</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">interval</span><span class="token punctuation">:</span> 1m
|
||||
<span class="token key atrule">threshold</span><span class="token punctuation">:</span> <span class="token number">10</span>
|
||||
<span class="token key atrule">iterations</span><span class="token punctuation">:</span> <span class="token number">2</span>
|
||||
<span class="token key atrule">match</span><span class="token punctuation">:</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">headers</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">x-canary</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">exact</span><span class="token punctuation">:</span> <span class="token string">"insider"</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">headers</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">cookie</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">exact</span><span class="token punctuation">:</span> <span class="token string">"canary"</span>
|
||||
</code></pre></div><p>Note that the NGINX ingress controller supports only exact matching for a single header and the cookie value is set to <code>always</code>.</p> <p>The above configurations will route users with the x-canary header or canary cookie to the canary instance during analysis:</p> <div class="language-bash extra-class"><pre class="language-bash"><code><span class="token function">curl</span> -H <span class="token string">'X-Canary: insider'</span> http://app.example.com
|
||||
<span class="token function">curl</span> -b <span class="token string">'canary=always'</span> http://app.example.com
|
||||
</code></pre></div><h2 id="blue-green-deployments"><a href="#blue-green-deployments" aria-hidden="true" class="header-anchor">#</a> Blue/Green Deployments</h2> <p>For applications that are not deployed on a service mesh, Flagger can orchestrate blue/green style deployments
|
||||
with Kubernetes L4 networking. When using Istio you have the option to mirror traffic between blue and green.</p> <p><img src="https://raw.githubusercontent.com/weaveworks/flagger/master/docs/diagrams/flagger-bluegreen-steps.png" alt="Flagger Blue/Green Stages"></p> <p>You can use the blue/green deployment strategy by replacing <code>stepWeight/maxWeight</code> with <code>iterations</code> in the <code>canaryAnalysis</code> spec:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code> <span class="token key atrule">analysis</span><span class="token punctuation">:</span>
|
||||
<span class="token comment"># schedule interval (default 60s)</span>
|
||||
<span class="token key atrule">interval</span><span class="token punctuation">:</span> 1m
|
||||
<span class="token comment"># total number of iterations</span>
|
||||
<span class="token key atrule">iterations</span><span class="token punctuation">:</span> <span class="token number">10</span>
|
||||
<span class="token comment"># max number of failed iterations before rollback</span>
|
||||
<span class="token key atrule">threshold</span><span class="token punctuation">:</span> <span class="token number">2</span>
|
||||
</code></pre></div><p>With the above configuration Flagger will run conformance and load tests on the canary pods for ten minutes.
|
||||
If the metrics analysis succeeds, live traffic will be switched from the old version to the new one when the
|
||||
canary is promoted.</p> <p>The blue/green deployment strategy is supported for all service mesh providers.</p> <p>Blue/Green rollout steps for service mesh:</p> <ul><li>detect new revision (deployment spec, secrets or configmaps changes)</li> <li>scale up the canary (green)</li> <li>run conformance tests for the canary pods</li> <li>run load tests and metric checks for the canary pods every minute</li> <li>abort the canary release if the failure threshold is reached</li> <li>route traffic to canary</li> <li>promote canary spec over primary (blue)</li> <li>wait for primary rollout</li> <li>route traffic to primary</li> <li>scale down canary</li></ul> <p>After the analysis finishes, the traffic is routed to the canary (green) before triggering the primary (blue)
|
||||
rolling update, this ensures a smooth transition to the new version avoiding dropping in-flight requests during
|
||||
the Kubernetes deployment rollout.</p> <h2 id="blue-green-with-traffic-mirroring"><a href="#blue-green-with-traffic-mirroring" aria-hidden="true" class="header-anchor">#</a> Blue/Green with Traffic Mirroring</h2> <p>Traffic Mirroring is a pre-stage in a Canary (progressive traffic shifting) or
|
||||
Blue/Green deployment strategy. Traffic mirroring will copy each incoming
|
||||
request, sending one request to the primary and one to the canary service.
|
||||
The response from the primary is sent back to the user. The response from the canary
|
||||
is discarded. Metrics are collected on both requests so that the deployment will
|
||||
only proceed if the canary metrics are healthy.</p> <p>Mirroring should be used for requests that are <strong>idempotent</strong> or capable of
|
||||
being processed twice (once by the primary and once by the canary). Reads are
|
||||
idempotent. Before using mirroring on requests that may be writes, you should
|
||||
consider what will happen if a write is duplicated and handled by the primary
|
||||
and canary.</p> <p>To use mirroring, set <code>spec.canaryAnalysis.mirror</code> to <code>true</code>.</p> <p>Istio example:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code> <span class="token key atrule">analysis</span><span class="token punctuation">:</span>
|
||||
<span class="token comment"># schedule interval (default 60s)</span>
|
||||
<span class="token key atrule">interval</span><span class="token punctuation">:</span> 1m
|
||||
<span class="token comment"># total number of iterations</span>
|
||||
<span class="token key atrule">iterations</span><span class="token punctuation">:</span> <span class="token number">10</span>
|
||||
<span class="token comment"># max number of failed iterations before rollback</span>
|
||||
<span class="token key atrule">threshold</span><span class="token punctuation">:</span> <span class="token number">2</span>
|
||||
<span class="token comment"># Traffic shadowing (compatible with Istio only)</span>
|
||||
<span class="token key atrule">mirror</span><span class="token punctuation">:</span> <span class="token boolean important">true</span>
|
||||
</code></pre></div><p>Mirroring rollout steps for service mesh:</p> <ul><li>detect new revision (deployment spec, secrets or configmaps changes)</li> <li>scale from zero the canary deployment</li> <li>wait for the HPA to set the canary minimum replicas</li> <li>check canary pods health</li> <li>run the acceptance tests</li> <li>abort the canary release if tests fail</li> <li>start the load tests</li> <li>mirror traffic from primary to canary</li> <li>check request success rate and request duration every minute</li> <li>abort the canary release if the failure threshold is reached</li> <li>stop traffic mirroring after the number of iterations is reached</li> <li>route live traffic to the canary pods</li> <li>promote the canary (update the primary secrets, configmaps and deployment spec)</li> <li>wait for the primary deployment rollout to finish</li> <li>wait for the HPA to set the primary minimum replicas</li> <li>check primary pods health</li> <li>switch live traffic back to primary</li> <li>scale to zero the canary</li> <li>send notification with the canary analysis result</li></ul> <p>After the analysis finishes, the traffic is routed to the canary (green) before triggering the primary (blue)
|
||||
rolling update, this ensures a smooth transition to the new version avoiding dropping in-flight requests during
|
||||
the Kubernetes deployment rollout.</p></div> <footer class="page-edit"><!----> <!----></footer> <div class="page-nav"><p class="inner"><span class="prev">
|
||||
←
|
||||
<a href="/usage/how-it-works.html" class="prev">
|
||||
How it works
|
||||
</a></span> <span class="next"><a href="/usage/metrics.html">
|
||||
Metrics Analysis
|
||||
</a>
|
||||
→
|
||||
</span></p></div> </main></div><div class="global-ui"></div></div>
|
||||
<script src="/assets/js/app.b4b27991.js" defer></script><script src="/assets/js/2.ba5bf77c.js" defer></script><script src="/assets/js/31.fbfb336c.js" defer></script>
|
||||
</body>
|
||||
</html>
|
||||
File diff suppressed because one or more lines are too long
@@ -0,0 +1,35 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en-US">
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<meta name="viewport" content="width=device-width,initial-scale=1">
|
||||
<title>Flagger</title>
|
||||
<meta name="description" content="Progressive Delivery operator for Kubernetes (Canary, A/B Testing and Blue/Green deployments)">
|
||||
<link rel="icon" href="/favicon.png">
|
||||
<link rel="stylesheet" href="/website.css">
|
||||
<meta name="keywords" content="gitops kubernetes flagger istio linkerd appmesh contour gloo nginx">
|
||||
<meta name="twitter:card" content="summary_large_image">
|
||||
<meta name="twitter:title" content="Flagger">
|
||||
<meta name="twitter:description" content="Progressive delivery Kubernetes operator (Canary, A/B Testing and Blue/Green deployments)">
|
||||
<meta name="twitter:image:src" content="https://flagger.app/flagger-overview.png">
|
||||
|
||||
<link rel="preload" href="/assets/css/0.styles.a0ada997.css" as="style"><link rel="preload" href="/assets/js/app.b4b27991.js" as="script"><link rel="preload" href="/assets/js/2.ba5bf77c.js" as="script"><link rel="preload" href="/assets/js/29.17c547e6.js" as="script"><link rel="prefetch" href="/assets/js/10.bf6f38d4.js"><link rel="prefetch" href="/assets/js/11.3af38cfe.js"><link rel="prefetch" href="/assets/js/12.eca4b89c.js"><link rel="prefetch" href="/assets/js/13.9104349a.js"><link rel="prefetch" href="/assets/js/14.a4f3d810.js"><link rel="prefetch" href="/assets/js/15.aada2caa.js"><link rel="prefetch" href="/assets/js/16.3012a10b.js"><link rel="prefetch" href="/assets/js/17.a98b6aa9.js"><link rel="prefetch" href="/assets/js/18.e5188926.js"><link rel="prefetch" href="/assets/js/19.bb9498f7.js"><link rel="prefetch" href="/assets/js/20.dce5a04e.js"><link rel="prefetch" href="/assets/js/21.df66561d.js"><link rel="prefetch" href="/assets/js/22.1c5d14b9.js"><link rel="prefetch" href="/assets/js/23.b3dcc355.js"><link rel="prefetch" href="/assets/js/24.4f54d289.js"><link rel="prefetch" href="/assets/js/25.914acd1d.js"><link rel="prefetch" href="/assets/js/26.b2d4f402.js"><link rel="prefetch" href="/assets/js/27.ea9f1f9c.js"><link rel="prefetch" href="/assets/js/28.deae273d.js"><link rel="prefetch" href="/assets/js/3.8b254d5d.js"><link rel="prefetch" href="/assets/js/30.38bd809e.js"><link rel="prefetch" href="/assets/js/31.fbfb336c.js"><link rel="prefetch" href="/assets/js/32.591c3f2b.js"><link rel="prefetch" href="/assets/js/33.c456709f.js"><link rel="prefetch" href="/assets/js/34.5a071e36.js"><link rel="prefetch" href="/assets/js/35.fc27c09e.js"><link rel="prefetch" href="/assets/js/36.144098aa.js"><link rel="prefetch" href="/assets/js/4.26a3069c.js"><link rel="prefetch" href="/assets/js/5.f92a6aca.js"><link rel="prefetch" href="/assets/js/6.ee5ffca3.js"><link rel="prefetch" href="/assets/js/7.6bf27a87.js"><link rel="prefetch" href="/assets/js/8.8b72a8d3.js"><link rel="prefetch" href="/assets/js/9.7919fc1d.js">
|
||||
<link rel="stylesheet" href="/assets/css/0.styles.a0ada997.css">
|
||||
</head>
|
||||
<body>
|
||||
<div id="app" data-server-rendered="true"><div class="theme-container"><header class="navbar"><div class="sidebar-button"><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" role="img" viewBox="0 0 448 512" class="icon"><path fill="currentColor" d="M436 124H12c-6.627 0-12-5.373-12-12V80c0-6.627 5.373-12 12-12h424c6.627 0 12 5.373 12 12v32c0 6.627-5.373 12-12 12zm0 160H12c-6.627 0-12-5.373-12-12v-32c0-6.627 5.373-12 12-12h424c6.627 0 12 5.373 12 12v32c0 6.627-5.373 12-12 12zm0 160H12c-6.627 0-12-5.373-12-12v-32c0-6.627 5.373-12 12-12h424c6.627 0 12 5.373 12 12v32c0 6.627-5.373 12-12 12z"></path></svg></div> <a href="/" class="home-link router-link-active"><!----> <span class="site-name">Flagger</span></a> <div class="links"><div class="search-box"><input aria-label="Search" autocomplete="off" spellcheck="false" value=""> <!----></div> <nav class="nav-links can-hide"><div class="nav-item"><a href="https://docs.flagger.app" target="_blank" rel="noopener noreferrer" class="nav-link external">
|
||||
Docs
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></div><div class="nav-item"><a href="https://github.com/weaveworks/flagger/blob/master/CHANGELOG.md" target="_blank" rel="noopener noreferrer" class="nav-link external">
|
||||
Changelog
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></div> <a href="https://github.com/weaveworks/flagger" target="_blank" rel="noopener noreferrer" class="repo-link">
|
||||
GitHub
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></nav></div></header> <div class="sidebar-mask"></div> <aside class="sidebar"><nav class="nav-links"><div class="nav-item"><a href="https://docs.flagger.app" target="_blank" rel="noopener noreferrer" class="nav-link external">
|
||||
Docs
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></div><div class="nav-item"><a href="https://github.com/weaveworks/flagger/blob/master/CHANGELOG.md" target="_blank" rel="noopener noreferrer" class="nav-link external">
|
||||
Changelog
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></div> <a href="https://github.com/weaveworks/flagger" target="_blank" rel="noopener noreferrer" class="repo-link">
|
||||
GitHub
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></nav> <ul class="sidebar-links"><li><a href="/" class="sidebar-link">Home</a></li><li><section class="sidebar-group depth-0"><a href="/intro/" class="sidebar-heading clickable"><span>Introduction</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/intro/" class="sidebar-link">Get Started</a></li><li><a href="/intro/faq.html" class="sidebar-link">FAQ</a></li></ul></section></li><li><section class="sidebar-group depth-0"><a href="/install/flagger-install-on-kubernetes" class="sidebar-heading clickable"><span>Install</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/install/flagger-install-on-kubernetes.html" class="sidebar-link">On Kubernetes</a></li><li><a href="/install/flagger-install-on-google-cloud.html" class="sidebar-link">On GKE Istio</a></li><li><a href="/install/flagger-install-on-eks-appmesh.html" class="sidebar-link">On EKS App Mesh</a></li></ul></section></li><li><section class="sidebar-group depth-0"><a href="/usage/how-it-works" class="sidebar-heading clickable"><span>Usage</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/usage/how-it-works.html" class="sidebar-link">How it works</a></li><li><a href="/usage/deployment-strategies.html" class="sidebar-link">Deployment Strategies</a></li><li><a href="/usage/metrics.html" class="sidebar-link">Metrics Analysis</a></li><li><a href="/usage/webhooks.html" class="sidebar-link">Webhooks</a></li><li><a href="/usage/alerting.html" class="sidebar-link">Alerting</a></li><li><a href="/usage/monitoring.html" class="sidebar-link">Monitoring</a></li></ul></section></li><li><section class="sidebar-group depth-0"><a href="/tutorials/istio-progressive-delivery" class="sidebar-heading clickable"><span>Tutorials</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/tutorials/istio-progressive-delivery.html" class="sidebar-link">Istio Canaries</a></li><li><a href="/tutorials/istio-ab-testing.html" class="sidebar-link">Istio A/B Testing</a></li><li><a href="/tutorials/linkerd-progressive-delivery.html" class="sidebar-link">Linkerd Canaries</a></li><li><a href="/tutorials/appmesh-progressive-delivery.html" class="sidebar-link">App Mesh Canaries</a></li><li><a href="/tutorials/nginx-progressive-delivery.html" class="sidebar-link">NGINX Ingress Canaries</a></li><li><a href="/tutorials/gloo-progressive-delivery.html" class="sidebar-link">Gloo Canaries</a></li><li><a href="/tutorials/contour-progressive-delivery.html" class="sidebar-link">Contour Canaries</a></li><li><a href="/tutorials/kubernetes-blue-green.html" class="sidebar-link">Kubernetes Blue/Green</a></li><li><a href="/tutorials/canary-helm-gitops.html" class="sidebar-link">Canaries with Helm charts and GitOps</a></li></ul></section></li><li><section class="sidebar-group depth-0"><a href="/dev/dev-guide" class="sidebar-heading clickable"><span>Dev</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/dev/dev-guide.html" class="sidebar-link">Development Guide</a></li><li><a href="/dev/release-guide.html" class="sidebar-link">Release Guide</a></li><li><a href="/dev/upgrade-guide.html" class="sidebar-link">Upgrade Guide</a></li></ul></section></li></ul> </aside> <main class="page"> <div class="theme-default-content content__default"></div> <footer class="page-edit"><!----> <!----></footer> <!----> </main></div><div class="global-ui"></div></div>
|
||||
<script src="/assets/js/app.b4b27991.js" defer></script><script src="/assets/js/2.ba5bf77c.js" defer></script><script src="/assets/js/29.17c547e6.js" defer></script>
|
||||
</body>
|
||||
</html>
|
||||
@@ -0,0 +1,265 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en-US">
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<meta name="viewport" content="width=device-width,initial-scale=1">
|
||||
<title>Metrics Analysis | Flagger</title>
|
||||
<meta name="description" content="Progressive Delivery operator for Kubernetes (Canary, A/B Testing and Blue/Green deployments)">
|
||||
<link rel="icon" href="/favicon.png">
|
||||
<link rel="stylesheet" href="/website.css">
|
||||
<meta name="keywords" content="gitops kubernetes flagger istio linkerd appmesh contour gloo nginx">
|
||||
<meta name="twitter:card" content="summary_large_image">
|
||||
<meta name="twitter:title" content="Flagger">
|
||||
<meta name="twitter:description" content="Progressive delivery Kubernetes operator (Canary, A/B Testing and Blue/Green deployments)">
|
||||
<meta name="twitter:image:src" content="https://flagger.app/flagger-overview.png">
|
||||
|
||||
<link rel="preload" href="/assets/css/0.styles.a0ada997.css" as="style"><link rel="preload" href="/assets/js/app.b4b27991.js" as="script"><link rel="preload" href="/assets/js/2.ba5bf77c.js" as="script"><link rel="preload" href="/assets/js/33.c456709f.js" as="script"><link rel="prefetch" href="/assets/js/10.bf6f38d4.js"><link rel="prefetch" href="/assets/js/11.3af38cfe.js"><link rel="prefetch" href="/assets/js/12.eca4b89c.js"><link rel="prefetch" href="/assets/js/13.9104349a.js"><link rel="prefetch" href="/assets/js/14.a4f3d810.js"><link rel="prefetch" href="/assets/js/15.aada2caa.js"><link rel="prefetch" href="/assets/js/16.3012a10b.js"><link rel="prefetch" href="/assets/js/17.a98b6aa9.js"><link rel="prefetch" href="/assets/js/18.e5188926.js"><link rel="prefetch" href="/assets/js/19.bb9498f7.js"><link rel="prefetch" href="/assets/js/20.dce5a04e.js"><link rel="prefetch" href="/assets/js/21.df66561d.js"><link rel="prefetch" href="/assets/js/22.1c5d14b9.js"><link rel="prefetch" href="/assets/js/23.b3dcc355.js"><link rel="prefetch" href="/assets/js/24.4f54d289.js"><link rel="prefetch" href="/assets/js/25.914acd1d.js"><link rel="prefetch" href="/assets/js/26.b2d4f402.js"><link rel="prefetch" href="/assets/js/27.ea9f1f9c.js"><link rel="prefetch" href="/assets/js/28.deae273d.js"><link rel="prefetch" href="/assets/js/29.17c547e6.js"><link rel="prefetch" href="/assets/js/3.8b254d5d.js"><link rel="prefetch" href="/assets/js/30.38bd809e.js"><link rel="prefetch" href="/assets/js/31.fbfb336c.js"><link rel="prefetch" href="/assets/js/32.591c3f2b.js"><link rel="prefetch" href="/assets/js/34.5a071e36.js"><link rel="prefetch" href="/assets/js/35.fc27c09e.js"><link rel="prefetch" href="/assets/js/36.144098aa.js"><link rel="prefetch" href="/assets/js/4.26a3069c.js"><link rel="prefetch" href="/assets/js/5.f92a6aca.js"><link rel="prefetch" href="/assets/js/6.ee5ffca3.js"><link rel="prefetch" href="/assets/js/7.6bf27a87.js"><link rel="prefetch" href="/assets/js/8.8b72a8d3.js"><link rel="prefetch" href="/assets/js/9.7919fc1d.js">
|
||||
<link rel="stylesheet" href="/assets/css/0.styles.a0ada997.css">
|
||||
</head>
|
||||
<body>
|
||||
<div id="app" data-server-rendered="true"><div class="theme-container"><header class="navbar"><div class="sidebar-button"><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" role="img" viewBox="0 0 448 512" class="icon"><path fill="currentColor" d="M436 124H12c-6.627 0-12-5.373-12-12V80c0-6.627 5.373-12 12-12h424c6.627 0 12 5.373 12 12v32c0 6.627-5.373 12-12 12zm0 160H12c-6.627 0-12-5.373-12-12v-32c0-6.627 5.373-12 12-12h424c6.627 0 12 5.373 12 12v32c0 6.627-5.373 12-12 12zm0 160H12c-6.627 0-12-5.373-12-12v-32c0-6.627 5.373-12 12-12h424c6.627 0 12 5.373 12 12v32c0 6.627-5.373 12-12 12z"></path></svg></div> <a href="/" class="home-link router-link-active"><!----> <span class="site-name">Flagger</span></a> <div class="links"><div class="search-box"><input aria-label="Search" autocomplete="off" spellcheck="false" value=""> <!----></div> <nav class="nav-links can-hide"><div class="nav-item"><a href="https://docs.flagger.app" target="_blank" rel="noopener noreferrer" class="nav-link external">
|
||||
Docs
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></div><div class="nav-item"><a href="https://github.com/weaveworks/flagger/blob/master/CHANGELOG.md" target="_blank" rel="noopener noreferrer" class="nav-link external">
|
||||
Changelog
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></div> <a href="https://github.com/weaveworks/flagger" target="_blank" rel="noopener noreferrer" class="repo-link">
|
||||
GitHub
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></nav></div></header> <div class="sidebar-mask"></div> <aside class="sidebar"><nav class="nav-links"><div class="nav-item"><a href="https://docs.flagger.app" target="_blank" rel="noopener noreferrer" class="nav-link external">
|
||||
Docs
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></div><div class="nav-item"><a href="https://github.com/weaveworks/flagger/blob/master/CHANGELOG.md" target="_blank" rel="noopener noreferrer" class="nav-link external">
|
||||
Changelog
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></div> <a href="https://github.com/weaveworks/flagger" target="_blank" rel="noopener noreferrer" class="repo-link">
|
||||
GitHub
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></nav> <ul class="sidebar-links"><li><a href="/" class="sidebar-link">Home</a></li><li><section class="sidebar-group depth-0"><a href="/intro/" class="sidebar-heading clickable"><span>Introduction</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/intro/" class="sidebar-link">Get Started</a></li><li><a href="/intro/faq.html" class="sidebar-link">FAQ</a></li></ul></section></li><li><section class="sidebar-group depth-0"><a href="/install/flagger-install-on-kubernetes" class="sidebar-heading clickable"><span>Install</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/install/flagger-install-on-kubernetes.html" class="sidebar-link">On Kubernetes</a></li><li><a href="/install/flagger-install-on-google-cloud.html" class="sidebar-link">On GKE Istio</a></li><li><a href="/install/flagger-install-on-eks-appmesh.html" class="sidebar-link">On EKS App Mesh</a></li></ul></section></li><li><section class="sidebar-group depth-0"><a href="/usage/how-it-works" class="sidebar-heading clickable open"><span>Usage</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/usage/how-it-works.html" class="sidebar-link">How it works</a></li><li><a href="/usage/deployment-strategies.html" class="sidebar-link">Deployment Strategies</a></li><li><a href="/usage/metrics.html" class="active sidebar-link">Metrics Analysis</a><ul class="sidebar-sub-headers"><li class="sidebar-sub-header"><a href="/usage/metrics.html#builtin-metrics" class="sidebar-link">Builtin metrics</a></li><li class="sidebar-sub-header"><a href="/usage/metrics.html#custom-metrics" class="sidebar-link">Custom metrics</a></li><li class="sidebar-sub-header"><a href="/usage/metrics.html#prometheus" class="sidebar-link">Prometheus</a></li><li class="sidebar-sub-header"><a href="/usage/metrics.html#datadog" class="sidebar-link">Datadog</a></li><li class="sidebar-sub-header"><a href="/usage/metrics.html#amazon-cloudwatch" class="sidebar-link">Amazon CloudWatch</a></li></ul></li><li><a href="/usage/webhooks.html" class="sidebar-link">Webhooks</a></li><li><a href="/usage/alerting.html" class="sidebar-link">Alerting</a></li><li><a href="/usage/monitoring.html" class="sidebar-link">Monitoring</a></li></ul></section></li><li><section class="sidebar-group depth-0"><a href="/tutorials/istio-progressive-delivery" class="sidebar-heading clickable"><span>Tutorials</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/tutorials/istio-progressive-delivery.html" class="sidebar-link">Istio Canaries</a></li><li><a href="/tutorials/istio-ab-testing.html" class="sidebar-link">Istio A/B Testing</a></li><li><a href="/tutorials/linkerd-progressive-delivery.html" class="sidebar-link">Linkerd Canaries</a></li><li><a href="/tutorials/appmesh-progressive-delivery.html" class="sidebar-link">App Mesh Canaries</a></li><li><a href="/tutorials/nginx-progressive-delivery.html" class="sidebar-link">NGINX Ingress Canaries</a></li><li><a href="/tutorials/gloo-progressive-delivery.html" class="sidebar-link">Gloo Canaries</a></li><li><a href="/tutorials/contour-progressive-delivery.html" class="sidebar-link">Contour Canaries</a></li><li><a href="/tutorials/kubernetes-blue-green.html" class="sidebar-link">Kubernetes Blue/Green</a></li><li><a href="/tutorials/canary-helm-gitops.html" class="sidebar-link">Canaries with Helm charts and GitOps</a></li></ul></section></li><li><section class="sidebar-group depth-0"><a href="/dev/dev-guide" class="sidebar-heading clickable"><span>Dev</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/dev/dev-guide.html" class="sidebar-link">Development Guide</a></li><li><a href="/dev/release-guide.html" class="sidebar-link">Release Guide</a></li><li><a href="/dev/upgrade-guide.html" class="sidebar-link">Upgrade Guide</a></li></ul></section></li></ul> </aside> <main class="page"> <div class="theme-default-content content__default"><h1 id="metrics-analysis"><a href="#metrics-analysis" aria-hidden="true" class="header-anchor">#</a> Metrics Analysis</h1> <p>As part of the analysis process, Flagger can validate service level objectives (SLOs) like
|
||||
availability, error rate percentage, average response time and any other objective based on app specific metrics.
|
||||
If a drop in performance is noticed during the SLOs analysis,
|
||||
the release will be automatically rolled back with minimum impact to end-users.</p> <h2 id="builtin-metrics"><a href="#builtin-metrics" aria-hidden="true" class="header-anchor">#</a> Builtin metrics</h2> <p>Flagger comes with two builtin metric checks: HTTP request success rate and duration.</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code> <span class="token key atrule">analysis</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">metrics</span><span class="token punctuation">:</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> request<span class="token punctuation">-</span>success<span class="token punctuation">-</span>rate
|
||||
<span class="token key atrule">interval</span><span class="token punctuation">:</span> 1m
|
||||
<span class="token comment"># minimum req success rate (non 5xx responses)</span>
|
||||
<span class="token comment"># percentage (0-100)</span>
|
||||
<span class="token key atrule">thresholdRange</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">min</span><span class="token punctuation">:</span> <span class="token number">99</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> request<span class="token punctuation">-</span>duration
|
||||
<span class="token key atrule">interval</span><span class="token punctuation">:</span> 1m
|
||||
<span class="token comment"># maximum req duration P99</span>
|
||||
<span class="token comment"># milliseconds</span>
|
||||
<span class="token key atrule">thresholdRange</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">max</span><span class="token punctuation">:</span> <span class="token number">500</span>
|
||||
</code></pre></div><p>For each metric you can specify a range of accepted values with <code>thresholdRange</code>
|
||||
and the window size or the time series with <code>interval</code>.
|
||||
The builtin checks are available for every service mesh / ingress controller
|
||||
and are implemented with <a href="/faq.html#metrics">Prometheus queries</a>.</p> <h2 id="custom-metrics"><a href="#custom-metrics" aria-hidden="true" class="header-anchor">#</a> Custom metrics</h2> <p>The canary analysis can be extended with custom metric checks. Using a <code>MetricTemplate</code> custom resource, you
|
||||
configure Flagger to connect to a metric provider and run a query that returns a <code>float64</code> value.
|
||||
The query result is used to validate the canary based on the specified threshold range.</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code><span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> flagger.app/v1beta1
|
||||
<span class="token key atrule">kind</span><span class="token punctuation">:</span> MetricTemplate
|
||||
<span class="token key atrule">metadata</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">name</span><span class="token punctuation">:</span> my<span class="token punctuation">-</span>metric
|
||||
<span class="token key atrule">spec</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">provider</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> <span class="token comment"># can be prometheus or datadog</span>
|
||||
<span class="token key atrule">address</span><span class="token punctuation">:</span> <span class="token comment"># API URL</span>
|
||||
<span class="token key atrule">secretRef</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">name</span><span class="token punctuation">:</span> <span class="token comment"># name of the secret containing the API credentials</span>
|
||||
<span class="token key atrule">query</span><span class="token punctuation">:</span> <span class="token comment"># metric query</span>
|
||||
</code></pre></div><p>The following variables are available in query templates:</p> <ul><li><code>name</code> (canary.metadata.name)</li> <li><code>namespace</code> (canary.metadata.namespace)</li> <li><code>target</code> (canary.spec.targetRef.name)</li> <li><code>service</code> (canary.spec.service.name)</li> <li><code>ingress</code> (canary.spec.ingresRef.name)</li> <li><code>interval</code> (canary.spec.canaryAnalysis.metrics[].interval)</li></ul> <p>A canary analysis metric can reference a template with <code>templateRef</code>:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code> <span class="token key atrule">analysis</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">metrics</span><span class="token punctuation">:</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> <span class="token string">"my metric"</span>
|
||||
<span class="token key atrule">templateRef</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">name</span><span class="token punctuation">:</span> my<span class="token punctuation">-</span>metric
|
||||
<span class="token comment"># namespace is optional</span>
|
||||
<span class="token comment"># when not specified, the canary namespace will be used</span>
|
||||
<span class="token key atrule">namespace</span><span class="token punctuation">:</span> flagger
|
||||
<span class="token comment"># accepted values</span>
|
||||
<span class="token key atrule">thresholdRange</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">min</span><span class="token punctuation">:</span> <span class="token number">10</span>
|
||||
<span class="token key atrule">max</span><span class="token punctuation">:</span> <span class="token number">1000</span>
|
||||
<span class="token comment"># metric query time window</span>
|
||||
<span class="token key atrule">interval</span><span class="token punctuation">:</span> 1m
|
||||
</code></pre></div><h2 id="prometheus"><a href="#prometheus" aria-hidden="true" class="header-anchor">#</a> Prometheus</h2> <p>You can create custom metric checks targeting a Prometheus server
|
||||
by setting the provider type to <code>prometheus</code> and writing the query in PromQL.</p> <p>Prometheus template example:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code><span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> flagger.app/v1beta1
|
||||
<span class="token key atrule">kind</span><span class="token punctuation">:</span> MetricTemplate
|
||||
<span class="token key atrule">metadata</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">name</span><span class="token punctuation">:</span> not<span class="token punctuation">-</span>found<span class="token punctuation">-</span>percentage
|
||||
<span class="token key atrule">namespace</span><span class="token punctuation">:</span> istio<span class="token punctuation">-</span>system
|
||||
<span class="token key atrule">spec</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">provider</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> prometheus
|
||||
<span class="token key atrule">address</span><span class="token punctuation">:</span> http<span class="token punctuation">:</span>//promethues.istio<span class="token punctuation">-</span>system<span class="token punctuation">:</span><span class="token number">9090</span>
|
||||
<span class="token key atrule">query</span><span class="token punctuation">:</span> <span class="token punctuation">|</span><span class="token scalar string">
|
||||
100 - sum(
|
||||
rate(
|
||||
istio_requests_total{
|
||||
reporter="destination",
|
||||
destination_workload_namespace="{{ namespace }}",
|
||||
destination_workload="{{ target }}",
|
||||
response_code!="404"
|
||||
}[{{ interval }}]
|
||||
)
|
||||
)
|
||||
/
|
||||
sum(
|
||||
rate(
|
||||
istio_requests_total{
|
||||
reporter="destination",
|
||||
destination_workload_namespace="{{ namespace }}",
|
||||
destination_workload="{{ target }}"
|
||||
}[{{ interval }}]
|
||||
)
|
||||
) * 100</span>
|
||||
</code></pre></div><p>Reference the template in the canary analysis:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code> <span class="token key atrule">analysis</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">metrics</span><span class="token punctuation">:</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> <span class="token string">"404s percentage"</span>
|
||||
<span class="token key atrule">templateRef</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">name</span><span class="token punctuation">:</span> not<span class="token punctuation">-</span>found<span class="token punctuation">-</span>percentage
|
||||
<span class="token key atrule">namespace</span><span class="token punctuation">:</span> istio<span class="token punctuation">-</span>system
|
||||
<span class="token key atrule">thresholdRange</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">max</span><span class="token punctuation">:</span> <span class="token number">5</span>
|
||||
<span class="token key atrule">interval</span><span class="token punctuation">:</span> 1m
|
||||
</code></pre></div><p>The above configuration validates the canary by checking
|
||||
if the HTTP 404 req/sec percentage is below 5 percent of the total traffic.
|
||||
If the 404s rate reaches the 5% threshold, then the canary fails.</p> <p>Prometheus gRPC error rate example:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code><span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> flagger.app/v1beta1
|
||||
<span class="token key atrule">kind</span><span class="token punctuation">:</span> MetricTemplate
|
||||
<span class="token key atrule">metadata</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">name</span><span class="token punctuation">:</span> grpc<span class="token punctuation">-</span>error<span class="token punctuation">-</span>rate<span class="token punctuation">-</span>percentage
|
||||
<span class="token key atrule">namespace</span><span class="token punctuation">:</span> flagger
|
||||
<span class="token key atrule">spec</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">provider</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> prometheus
|
||||
<span class="token key atrule">address</span><span class="token punctuation">:</span> http<span class="token punctuation">:</span>//flagger<span class="token punctuation">-</span>promethues.flagger<span class="token punctuation">-</span>system<span class="token punctuation">:</span><span class="token number">9090</span>
|
||||
<span class="token key atrule">query</span><span class="token punctuation">:</span> <span class="token punctuation">|</span><span class="token scalar string">
|
||||
100 - sum(
|
||||
rate(
|
||||
grpc_server_handled_total{
|
||||
grpc_code!="OK",
|
||||
kubernetes_namespace="{{ namespace }}",
|
||||
kubernetes_pod_name=~"{{ target }}-[0-9a-zA-Z]+(-[0-9a-zA-Z]+)"
|
||||
}[{{ interval }}]
|
||||
)
|
||||
)
|
||||
/
|
||||
sum(
|
||||
rate(
|
||||
grpc_server_started_total{
|
||||
kubernetes_namespace="{{ namespace }}",
|
||||
kubernetes_pod_name=~"{{ target }}-[0-9a-zA-Z]+(-[0-9a-zA-Z]+)"
|
||||
}[{{ interval }}]
|
||||
)
|
||||
) * 100</span>
|
||||
</code></pre></div><p>The above template is for gPRC services instrumented with <a href="https://github.com/grpc-ecosystem/go-grpc-prometheus" target="_blank" rel="noopener noreferrer">go-grpc-prometheus<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a>.</p> <h2 id="datadog"><a href="#datadog" aria-hidden="true" class="header-anchor">#</a> Datadog</h2> <p>You can create custom metric checks using the Datadog provider.</p> <p>Create a secret with your Datadog API credentials:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code><span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> v1
|
||||
<span class="token key atrule">kind</span><span class="token punctuation">:</span> Secret
|
||||
<span class="token key atrule">metadata</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">name</span><span class="token punctuation">:</span> datadog
|
||||
<span class="token key atrule">namespace</span><span class="token punctuation">:</span> istio<span class="token punctuation">-</span>system
|
||||
<span class="token key atrule">data</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">datadog_api_key</span><span class="token punctuation">:</span> your<span class="token punctuation">-</span>datadog<span class="token punctuation">-</span>api<span class="token punctuation">-</span>key
|
||||
<span class="token key atrule">datadog_application_key</span><span class="token punctuation">:</span> your<span class="token punctuation">-</span>datadog<span class="token punctuation">-</span>application<span class="token punctuation">-</span>key
|
||||
</code></pre></div><p>Datadog template example:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code><span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> flagger.app/v1beta1
|
||||
<span class="token key atrule">kind</span><span class="token punctuation">:</span> MetricTemplate
|
||||
<span class="token key atrule">metadata</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">name</span><span class="token punctuation">:</span> not<span class="token punctuation">-</span>found<span class="token punctuation">-</span>percentage
|
||||
<span class="token key atrule">namespace</span><span class="token punctuation">:</span> istio<span class="token punctuation">-</span>system
|
||||
<span class="token key atrule">spec</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">provider</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> datadog
|
||||
<span class="token key atrule">address</span><span class="token punctuation">:</span> https<span class="token punctuation">:</span>//api.datadoghq.com
|
||||
<span class="token key atrule">secretRef</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">name</span><span class="token punctuation">:</span> datadog
|
||||
<span class="token key atrule">query</span><span class="token punctuation">:</span> <span class="token punctuation">|</span><span class="token scalar string">
|
||||
100 - (
|
||||
sum:istio.mesh.request.count{
|
||||
reporter:destination,
|
||||
destination_workload_namespace:{{ namespace }},
|
||||
destination_workload:{{ target }},
|
||||
!response_code:404
|
||||
}.as_count()
|
||||
/
|
||||
sum:istio.mesh.request.count{
|
||||
reporter:destination,
|
||||
destination_workload_namespace:{{ namespace }},
|
||||
destination_workload:{{ target }}
|
||||
}.as_count()
|
||||
) * 100</span>
|
||||
</code></pre></div><p>Reference the template in the canary analysis:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code> <span class="token key atrule">analysis</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">metrics</span><span class="token punctuation">:</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> <span class="token string">"404s percentage"</span>
|
||||
<span class="token key atrule">templateRef</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">name</span><span class="token punctuation">:</span> not<span class="token punctuation">-</span>found<span class="token punctuation">-</span>percentage
|
||||
<span class="token key atrule">namespace</span><span class="token punctuation">:</span> istio<span class="token punctuation">-</span>system
|
||||
<span class="token key atrule">thresholdRange</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">max</span><span class="token punctuation">:</span> <span class="token number">5</span>
|
||||
<span class="token key atrule">interval</span><span class="token punctuation">:</span> 1m
|
||||
</code></pre></div><h2 id="amazon-cloudwatch"><a href="#amazon-cloudwatch" aria-hidden="true" class="header-anchor">#</a> Amazon CloudWatch</h2> <p>You can create custom metric checks using the CloudWatch metrics provider.</p> <p>CloudWatch template example:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code><span class="token key atrule">apiVersion</span><span class="token punctuation">:</span> flagger.app/v1alpha1
|
||||
<span class="token key atrule">kind</span><span class="token punctuation">:</span> MetricTemplate
|
||||
<span class="token key atrule">metadata</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">name</span><span class="token punctuation">:</span> cloudwatch<span class="token punctuation">-</span>error<span class="token punctuation">-</span>rate
|
||||
<span class="token key atrule">spec</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">provider</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> cloudwatch
|
||||
<span class="token key atrule">region</span><span class="token punctuation">:</span> ap<span class="token punctuation">-</span>northeast<span class="token punctuation">-</span><span class="token number">1 </span><span class="token comment"># specify the region of your metrics</span>
|
||||
<span class="token key atrule">query</span><span class="token punctuation">:</span> <span class="token punctuation">|</span><span class="token scalar string">
|
||||
[
|
||||
{
|
||||
"Id": "e1",
|
||||
"Expression": "m1 / m2",
|
||||
"Label": "ErrorRate"
|
||||
},
|
||||
{
|
||||
"Id": "m1",
|
||||
"MetricStat": {
|
||||
"Metric": {
|
||||
"Namespace": "MyKubernetesCluster",
|
||||
"MetricName": "ErrorCount",
|
||||
"Dimensions": [
|
||||
{
|
||||
"Name": "appName",
|
||||
"Value": "{{ name }}.{{ namespace }}"
|
||||
}
|
||||
]
|
||||
},
|
||||
"Period": 60,
|
||||
"Stat": "Sum",
|
||||
"Unit": "Count"
|
||||
},
|
||||
"ReturnData": false
|
||||
},
|
||||
{
|
||||
"Id": "m2",
|
||||
"MetricStat": {
|
||||
"Metric": {
|
||||
"Namespace": "MyKubernetesCluster",
|
||||
"MetricName": "RequestCount",
|
||||
"Dimensions": [
|
||||
{
|
||||
"Name": "appName",
|
||||
"Value": "{{ name }}.{{ namespace }}"
|
||||
}
|
||||
]
|
||||
},
|
||||
"Period": 60,
|
||||
"Stat": "Sum",
|
||||
"Unit": "Count"
|
||||
},
|
||||
"ReturnData": false
|
||||
}
|
||||
]</span>
|
||||
</code></pre></div><p>The query format documentation can be found <a href="https://aws.amazon.com/premiumsupport/knowledge-center/cloudwatch-getmetricdata-api/" target="_blank" rel="noopener noreferrer">here<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a>.</p> <p>Reference the template in the canary analysis:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code> <span class="token key atrule">analysis</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">metrics</span><span class="token punctuation">:</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> <span class="token string">"app error rate"</span>
|
||||
<span class="token key atrule">templateRef</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">name</span><span class="token punctuation">:</span> cloudwatch<span class="token punctuation">-</span>error<span class="token punctuation">-</span>rate
|
||||
<span class="token key atrule">thresholdRange</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">max</span><span class="token punctuation">:</span> <span class="token number">0.1</span>
|
||||
<span class="token key atrule">interval</span><span class="token punctuation">:</span> 1m
|
||||
</code></pre></div><p><strong>Note</strong> that Flagger need AWS IAM permission to perform <code>cloudwatch:GetMetricData</code> to use this provider.</p></div> <footer class="page-edit"><!----> <!----></footer> <div class="page-nav"><p class="inner"><span class="prev">
|
||||
←
|
||||
<a href="/usage/deployment-strategies.html" class="prev">
|
||||
Deployment Strategies
|
||||
</a></span> <span class="next"><a href="/usage/webhooks.html">
|
||||
Webhooks
|
||||
</a>
|
||||
→
|
||||
</span></p></div> </main></div><div class="global-ui"></div></div>
|
||||
<script src="/assets/js/app.b4b27991.js" defer></script><script src="/assets/js/2.ba5bf77c.js" defer></script><script src="/assets/js/33.c456709f.js" defer></script>
|
||||
</body>
|
||||
</html>
|
||||
@@ -0,0 +1,111 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en-US">
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<meta name="viewport" content="width=device-width,initial-scale=1">
|
||||
<title>Monitoring | Flagger</title>
|
||||
<meta name="description" content="Progressive Delivery operator for Kubernetes (Canary, A/B Testing and Blue/Green deployments)">
|
||||
<link rel="icon" href="/favicon.png">
|
||||
<link rel="stylesheet" href="/website.css">
|
||||
<meta name="keywords" content="gitops kubernetes flagger istio linkerd appmesh contour gloo nginx">
|
||||
<meta name="twitter:card" content="summary_large_image">
|
||||
<meta name="twitter:title" content="Flagger">
|
||||
<meta name="twitter:description" content="Progressive delivery Kubernetes operator (Canary, A/B Testing and Blue/Green deployments)">
|
||||
<meta name="twitter:image:src" content="https://flagger.app/flagger-overview.png">
|
||||
|
||||
<link rel="preload" href="/assets/css/0.styles.a0ada997.css" as="style"><link rel="preload" href="/assets/js/app.b4b27991.js" as="script"><link rel="preload" href="/assets/js/2.ba5bf77c.js" as="script"><link rel="preload" href="/assets/js/34.5a071e36.js" as="script"><link rel="prefetch" href="/assets/js/10.bf6f38d4.js"><link rel="prefetch" href="/assets/js/11.3af38cfe.js"><link rel="prefetch" href="/assets/js/12.eca4b89c.js"><link rel="prefetch" href="/assets/js/13.9104349a.js"><link rel="prefetch" href="/assets/js/14.a4f3d810.js"><link rel="prefetch" href="/assets/js/15.aada2caa.js"><link rel="prefetch" href="/assets/js/16.3012a10b.js"><link rel="prefetch" href="/assets/js/17.a98b6aa9.js"><link rel="prefetch" href="/assets/js/18.e5188926.js"><link rel="prefetch" href="/assets/js/19.bb9498f7.js"><link rel="prefetch" href="/assets/js/20.dce5a04e.js"><link rel="prefetch" href="/assets/js/21.df66561d.js"><link rel="prefetch" href="/assets/js/22.1c5d14b9.js"><link rel="prefetch" href="/assets/js/23.b3dcc355.js"><link rel="prefetch" href="/assets/js/24.4f54d289.js"><link rel="prefetch" href="/assets/js/25.914acd1d.js"><link rel="prefetch" href="/assets/js/26.b2d4f402.js"><link rel="prefetch" href="/assets/js/27.ea9f1f9c.js"><link rel="prefetch" href="/assets/js/28.deae273d.js"><link rel="prefetch" href="/assets/js/29.17c547e6.js"><link rel="prefetch" href="/assets/js/3.8b254d5d.js"><link rel="prefetch" href="/assets/js/30.38bd809e.js"><link rel="prefetch" href="/assets/js/31.fbfb336c.js"><link rel="prefetch" href="/assets/js/32.591c3f2b.js"><link rel="prefetch" href="/assets/js/33.c456709f.js"><link rel="prefetch" href="/assets/js/35.fc27c09e.js"><link rel="prefetch" href="/assets/js/36.144098aa.js"><link rel="prefetch" href="/assets/js/4.26a3069c.js"><link rel="prefetch" href="/assets/js/5.f92a6aca.js"><link rel="prefetch" href="/assets/js/6.ee5ffca3.js"><link rel="prefetch" href="/assets/js/7.6bf27a87.js"><link rel="prefetch" href="/assets/js/8.8b72a8d3.js"><link rel="prefetch" href="/assets/js/9.7919fc1d.js">
|
||||
<link rel="stylesheet" href="/assets/css/0.styles.a0ada997.css">
|
||||
</head>
|
||||
<body>
|
||||
<div id="app" data-server-rendered="true"><div class="theme-container"><header class="navbar"><div class="sidebar-button"><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" role="img" viewBox="0 0 448 512" class="icon"><path fill="currentColor" d="M436 124H12c-6.627 0-12-5.373-12-12V80c0-6.627 5.373-12 12-12h424c6.627 0 12 5.373 12 12v32c0 6.627-5.373 12-12 12zm0 160H12c-6.627 0-12-5.373-12-12v-32c0-6.627 5.373-12 12-12h424c6.627 0 12 5.373 12 12v32c0 6.627-5.373 12-12 12zm0 160H12c-6.627 0-12-5.373-12-12v-32c0-6.627 5.373-12 12-12h424c6.627 0 12 5.373 12 12v32c0 6.627-5.373 12-12 12z"></path></svg></div> <a href="/" class="home-link router-link-active"><!----> <span class="site-name">Flagger</span></a> <div class="links"><div class="search-box"><input aria-label="Search" autocomplete="off" spellcheck="false" value=""> <!----></div> <nav class="nav-links can-hide"><div class="nav-item"><a href="https://docs.flagger.app" target="_blank" rel="noopener noreferrer" class="nav-link external">
|
||||
Docs
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></div><div class="nav-item"><a href="https://github.com/weaveworks/flagger/blob/master/CHANGELOG.md" target="_blank" rel="noopener noreferrer" class="nav-link external">
|
||||
Changelog
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></div> <a href="https://github.com/weaveworks/flagger" target="_blank" rel="noopener noreferrer" class="repo-link">
|
||||
GitHub
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></nav></div></header> <div class="sidebar-mask"></div> <aside class="sidebar"><nav class="nav-links"><div class="nav-item"><a href="https://docs.flagger.app" target="_blank" rel="noopener noreferrer" class="nav-link external">
|
||||
Docs
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></div><div class="nav-item"><a href="https://github.com/weaveworks/flagger/blob/master/CHANGELOG.md" target="_blank" rel="noopener noreferrer" class="nav-link external">
|
||||
Changelog
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></div> <a href="https://github.com/weaveworks/flagger" target="_blank" rel="noopener noreferrer" class="repo-link">
|
||||
GitHub
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></nav> <ul class="sidebar-links"><li><a href="/" class="sidebar-link">Home</a></li><li><section class="sidebar-group depth-0"><a href="/intro/" class="sidebar-heading clickable"><span>Introduction</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/intro/" class="sidebar-link">Get Started</a></li><li><a href="/intro/faq.html" class="sidebar-link">FAQ</a></li></ul></section></li><li><section class="sidebar-group depth-0"><a href="/install/flagger-install-on-kubernetes" class="sidebar-heading clickable"><span>Install</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/install/flagger-install-on-kubernetes.html" class="sidebar-link">On Kubernetes</a></li><li><a href="/install/flagger-install-on-google-cloud.html" class="sidebar-link">On GKE Istio</a></li><li><a href="/install/flagger-install-on-eks-appmesh.html" class="sidebar-link">On EKS App Mesh</a></li></ul></section></li><li><section class="sidebar-group depth-0"><a href="/usage/how-it-works" class="sidebar-heading clickable open"><span>Usage</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/usage/how-it-works.html" class="sidebar-link">How it works</a></li><li><a href="/usage/deployment-strategies.html" class="sidebar-link">Deployment Strategies</a></li><li><a href="/usage/metrics.html" class="sidebar-link">Metrics Analysis</a></li><li><a href="/usage/webhooks.html" class="sidebar-link">Webhooks</a></li><li><a href="/usage/alerting.html" class="sidebar-link">Alerting</a></li><li><a href="/usage/monitoring.html" class="active sidebar-link">Monitoring</a><ul class="sidebar-sub-headers"><li class="sidebar-sub-header"><a href="/usage/monitoring.html#grafana" class="sidebar-link">Grafana</a></li><li class="sidebar-sub-header"><a href="/usage/monitoring.html#logging" class="sidebar-link">Logging</a></li><li class="sidebar-sub-header"><a href="/usage/monitoring.html#event-webhook" class="sidebar-link">Event Webhook</a></li><li class="sidebar-sub-header"><a href="/usage/monitoring.html#metrics" class="sidebar-link">Metrics</a></li></ul></li></ul></section></li><li><section class="sidebar-group depth-0"><a href="/tutorials/istio-progressive-delivery" class="sidebar-heading clickable"><span>Tutorials</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/tutorials/istio-progressive-delivery.html" class="sidebar-link">Istio Canaries</a></li><li><a href="/tutorials/istio-ab-testing.html" class="sidebar-link">Istio A/B Testing</a></li><li><a href="/tutorials/linkerd-progressive-delivery.html" class="sidebar-link">Linkerd Canaries</a></li><li><a href="/tutorials/appmesh-progressive-delivery.html" class="sidebar-link">App Mesh Canaries</a></li><li><a href="/tutorials/nginx-progressive-delivery.html" class="sidebar-link">NGINX Ingress Canaries</a></li><li><a href="/tutorials/gloo-progressive-delivery.html" class="sidebar-link">Gloo Canaries</a></li><li><a href="/tutorials/contour-progressive-delivery.html" class="sidebar-link">Contour Canaries</a></li><li><a href="/tutorials/kubernetes-blue-green.html" class="sidebar-link">Kubernetes Blue/Green</a></li><li><a href="/tutorials/canary-helm-gitops.html" class="sidebar-link">Canaries with Helm charts and GitOps</a></li></ul></section></li><li><section class="sidebar-group depth-0"><a href="/dev/dev-guide" class="sidebar-heading clickable"><span>Dev</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/dev/dev-guide.html" class="sidebar-link">Development Guide</a></li><li><a href="/dev/release-guide.html" class="sidebar-link">Release Guide</a></li><li><a href="/dev/upgrade-guide.html" class="sidebar-link">Upgrade Guide</a></li></ul></section></li></ul> </aside> <main class="page"> <div class="theme-default-content content__default"><h1 id="monitoring"><a href="#monitoring" aria-hidden="true" class="header-anchor">#</a> Monitoring</h1> <h2 id="grafana"><a href="#grafana" aria-hidden="true" class="header-anchor">#</a> Grafana</h2> <p>Flagger comes with a Grafana dashboard made for canary analysis. Install Grafana with Helm:</p> <div class="language-bash extra-class"><pre class="language-bash"><code>helm upgrade -i flagger-grafana flagger/grafana <span class="token punctuation">\</span>
|
||||
--namespace<span class="token operator">=</span>istio-system <span class="token punctuation">\</span> <span class="token comment"># or appmesh-system</span>
|
||||
--set <span class="token assign-left variable">url</span><span class="token operator">=</span>http://prometheus:9090
|
||||
</code></pre></div><p>The dashboard shows the RED and USE metrics for the primary and canary workloads:</p> <p><img src="https://raw.githubusercontent.com/weaveworks/flagger/master/docs/screens/grafana-canary-analysis.png" alt="Canary Dashboard"></p> <h2 id="logging"><a href="#logging" aria-hidden="true" class="header-anchor">#</a> Logging</h2> <p>The canary errors and latency spikes have been recorded as Kubernetes events and logged by Flagger in json format:</p> <div class="language-text extra-class"><pre class="language-text"><code>kubectl -n istio-system logs deployment/flagger --tail=100 | jq .msg
|
||||
|
||||
Starting canary deployment for podinfo.test
|
||||
Advance podinfo.test canary weight 5
|
||||
Advance podinfo.test canary weight 10
|
||||
Advance podinfo.test canary weight 15
|
||||
Advance podinfo.test canary weight 20
|
||||
Advance podinfo.test canary weight 25
|
||||
Advance podinfo.test canary weight 30
|
||||
Advance podinfo.test canary weight 35
|
||||
Halt podinfo.test advancement success rate 98.69% < 99%
|
||||
Advance podinfo.test canary weight 40
|
||||
Halt podinfo.test advancement request duration 1.515s > 500ms
|
||||
Advance podinfo.test canary weight 45
|
||||
Advance podinfo.test canary weight 50
|
||||
Copying podinfo.test template spec to podinfo-primary.test
|
||||
Halt podinfo-primary.test advancement waiting for rollout to finish: 1 old replicas are pending termination
|
||||
Scaling down podinfo.test
|
||||
Promotion completed! podinfo.test
|
||||
</code></pre></div><h2 id="event-webhook"><a href="#event-webhook" aria-hidden="true" class="header-anchor">#</a> Event Webhook</h2> <p>Flagger can be configured to send event payloads to a specified webhook:</p> <div class="language-bash extra-class"><pre class="language-bash"><code>helm upgrade -i flagger flagger/flagger <span class="token punctuation">\</span>
|
||||
--set <span class="token assign-left variable">eventWebhook</span><span class="token operator">=</span>https://example.com/flagger-canary-event-webhook
|
||||
</code></pre></div><p>The environment variable <em>EVENT_WEBHOOK_URL</em> can be used for activating the event-webhook, too. This is handy for using a secret to store a sensible value that could contain api keys for example.</p> <p>When configured, every action that Flagger takes during a canary deployment will be sent as JSON via an HTTP POST request. The JSON payload has the following schema:</p> <div class="language-javascript extra-class"><pre class="language-javascript"><code><span class="token punctuation">{</span>
|
||||
<span class="token string">"name"</span><span class="token punctuation">:</span> <span class="token string">"string (canary name)"</span><span class="token punctuation">,</span>
|
||||
<span class="token string">"namespace"</span><span class="token punctuation">:</span> <span class="token string">"string (canary namespace)"</span><span class="token punctuation">,</span>
|
||||
<span class="token string">"phase"</span><span class="token punctuation">:</span> <span class="token string">"string (canary phase)"</span><span class="token punctuation">,</span>
|
||||
<span class="token string">"metadata"</span><span class="token punctuation">:</span> <span class="token punctuation">{</span>
|
||||
<span class="token string">"eventMessage"</span><span class="token punctuation">:</span> <span class="token string">"string (canary event message)"</span><span class="token punctuation">,</span>
|
||||
<span class="token string">"eventType"</span><span class="token punctuation">:</span> <span class="token string">"string (canary event type)"</span><span class="token punctuation">,</span>
|
||||
<span class="token string">"timestamp"</span><span class="token punctuation">:</span> <span class="token string">"string (unix timestamp ms)"</span>
|
||||
<span class="token punctuation">}</span>
|
||||
<span class="token punctuation">}</span>
|
||||
</code></pre></div><p>Example:</p> <div class="language-javascript extra-class"><pre class="language-javascript"><code><span class="token punctuation">{</span>
|
||||
<span class="token string">"name"</span><span class="token punctuation">:</span> <span class="token string">"podinfo"</span><span class="token punctuation">,</span>
|
||||
<span class="token string">"namespace"</span><span class="token punctuation">:</span> <span class="token string">"default"</span><span class="token punctuation">,</span>
|
||||
<span class="token string">"phase"</span><span class="token punctuation">:</span> <span class="token string">"Progressing"</span><span class="token punctuation">,</span>
|
||||
<span class="token string">"metadata"</span><span class="token punctuation">:</span> <span class="token punctuation">{</span>
|
||||
<span class="token string">"eventMessage"</span><span class="token punctuation">:</span> <span class="token string">"New revision detected! Scaling up podinfo.default"</span><span class="token punctuation">,</span>
|
||||
<span class="token string">"eventType"</span><span class="token punctuation">:</span> <span class="token string">"Normal"</span><span class="token punctuation">,</span>
|
||||
<span class="token string">"timestamp"</span><span class="token punctuation">:</span> <span class="token string">"1578607635167"</span>
|
||||
<span class="token punctuation">}</span>
|
||||
<span class="token punctuation">}</span>
|
||||
</code></pre></div><p>The event webhook can be overwritten at canary level with:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code> <span class="token key atrule">analysis</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">webhooks</span><span class="token punctuation">:</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> <span class="token string">"send to Slack"</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> event
|
||||
<span class="token key atrule">url</span><span class="token punctuation">:</span> http<span class="token punctuation">:</span>//event<span class="token punctuation">-</span>recevier.notifications/slack
|
||||
</code></pre></div><h2 id="metrics"><a href="#metrics" aria-hidden="true" class="header-anchor">#</a> Metrics</h2> <p>Flagger exposes Prometheus metrics that can be used to determine the canary analysis status and the destination weight values:</p> <div class="language-bash extra-class"><pre class="language-bash"><code><span class="token comment"># Flagger version and mesh provider gauge</span>
|
||||
flagger_info<span class="token punctuation">{</span>version<span class="token operator">=</span><span class="token string">"0.10.0"</span>, <span class="token assign-left variable">mesh_provider</span><span class="token operator">=</span><span class="token string">"istio"</span><span class="token punctuation">}</span> <span class="token number">1</span>
|
||||
|
||||
<span class="token comment"># Canaries total gauge</span>
|
||||
flagger_canary_total<span class="token punctuation">{</span>namespace<span class="token operator">=</span><span class="token string">"test"</span><span class="token punctuation">}</span> <span class="token number">1</span>
|
||||
|
||||
<span class="token comment"># Canary promotion last known status gauge</span>
|
||||
<span class="token comment"># 0 - running, 1 - successful, 2 - failed</span>
|
||||
flagger_canary_status<span class="token punctuation">{</span>name<span class="token operator">=</span><span class="token string">"podinfo"</span> <span class="token assign-left variable">namespace</span><span class="token operator">=</span><span class="token string">"test"</span><span class="token punctuation">}</span> <span class="token number">1</span>
|
||||
|
||||
<span class="token comment"># Canary traffic weight gauge</span>
|
||||
flagger_canary_weight<span class="token punctuation">{</span>workload<span class="token operator">=</span><span class="token string">"podinfo-primary"</span> <span class="token assign-left variable">namespace</span><span class="token operator">=</span><span class="token string">"test"</span><span class="token punctuation">}</span> <span class="token number">95</span>
|
||||
flagger_canary_weight<span class="token punctuation">{</span>workload<span class="token operator">=</span><span class="token string">"podinfo"</span> <span class="token assign-left variable">namespace</span><span class="token operator">=</span><span class="token string">"test"</span><span class="token punctuation">}</span> <span class="token number">5</span>
|
||||
|
||||
<span class="token comment"># Seconds spent performing canary analysis histogram</span>
|
||||
flagger_canary_duration_seconds_bucket<span class="token punctuation">{</span>name<span class="token operator">=</span><span class="token string">"podinfo"</span>,namespace<span class="token operator">=</span><span class="token string">"test"</span>,le<span class="token operator">=</span><span class="token string">"10"</span><span class="token punctuation">}</span> <span class="token number">6</span>
|
||||
flagger_canary_duration_seconds_bucket<span class="token punctuation">{</span>name<span class="token operator">=</span><span class="token string">"podinfo"</span>,namespace<span class="token operator">=</span><span class="token string">"test"</span>,le<span class="token operator">=</span><span class="token string">"+Inf"</span><span class="token punctuation">}</span> <span class="token number">6</span>
|
||||
flagger_canary_duration_seconds_sum<span class="token punctuation">{</span>name<span class="token operator">=</span><span class="token string">"podinfo"</span>,namespace<span class="token operator">=</span><span class="token string">"test"</span><span class="token punctuation">}</span> <span class="token number">17.3561329</span>
|
||||
flagger_canary_duration_seconds_count<span class="token punctuation">{</span>name<span class="token operator">=</span><span class="token string">"podinfo"</span>,namespace<span class="token operator">=</span><span class="token string">"test"</span><span class="token punctuation">}</span> <span class="token number">6</span>
|
||||
</code></pre></div></div> <footer class="page-edit"><!----> <!----></footer> <div class="page-nav"><p class="inner"><span class="prev">
|
||||
←
|
||||
<a href="/usage/alerting.html" class="prev">
|
||||
Alerting
|
||||
</a></span> <span class="next"><a href="/tutorials/istio-progressive-delivery.html">
|
||||
Istio Canaries
|
||||
</a>
|
||||
→
|
||||
</span></p></div> </main></div><div class="global-ui"></div></div>
|
||||
<script src="/assets/js/app.b4b27991.js" defer></script><script src="/assets/js/2.ba5bf77c.js" defer></script><script src="/assets/js/34.5a071e36.js" defer></script>
|
||||
</body>
|
||||
</html>
|
||||
@@ -0,0 +1,254 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en-US">
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<meta name="viewport" content="width=device-width,initial-scale=1">
|
||||
<title>Webhooks | Flagger</title>
|
||||
<meta name="description" content="Progressive Delivery operator for Kubernetes (Canary, A/B Testing and Blue/Green deployments)">
|
||||
<link rel="icon" href="/favicon.png">
|
||||
<link rel="stylesheet" href="/website.css">
|
||||
<meta name="keywords" content="gitops kubernetes flagger istio linkerd appmesh contour gloo nginx">
|
||||
<meta name="twitter:card" content="summary_large_image">
|
||||
<meta name="twitter:title" content="Flagger">
|
||||
<meta name="twitter:description" content="Progressive delivery Kubernetes operator (Canary, A/B Testing and Blue/Green deployments)">
|
||||
<meta name="twitter:image:src" content="https://flagger.app/flagger-overview.png">
|
||||
|
||||
<link rel="preload" href="/assets/css/0.styles.a0ada997.css" as="style"><link rel="preload" href="/assets/js/app.b4b27991.js" as="script"><link rel="preload" href="/assets/js/2.ba5bf77c.js" as="script"><link rel="preload" href="/assets/js/35.fc27c09e.js" as="script"><link rel="prefetch" href="/assets/js/10.bf6f38d4.js"><link rel="prefetch" href="/assets/js/11.3af38cfe.js"><link rel="prefetch" href="/assets/js/12.eca4b89c.js"><link rel="prefetch" href="/assets/js/13.9104349a.js"><link rel="prefetch" href="/assets/js/14.a4f3d810.js"><link rel="prefetch" href="/assets/js/15.aada2caa.js"><link rel="prefetch" href="/assets/js/16.3012a10b.js"><link rel="prefetch" href="/assets/js/17.a98b6aa9.js"><link rel="prefetch" href="/assets/js/18.e5188926.js"><link rel="prefetch" href="/assets/js/19.bb9498f7.js"><link rel="prefetch" href="/assets/js/20.dce5a04e.js"><link rel="prefetch" href="/assets/js/21.df66561d.js"><link rel="prefetch" href="/assets/js/22.1c5d14b9.js"><link rel="prefetch" href="/assets/js/23.b3dcc355.js"><link rel="prefetch" href="/assets/js/24.4f54d289.js"><link rel="prefetch" href="/assets/js/25.914acd1d.js"><link rel="prefetch" href="/assets/js/26.b2d4f402.js"><link rel="prefetch" href="/assets/js/27.ea9f1f9c.js"><link rel="prefetch" href="/assets/js/28.deae273d.js"><link rel="prefetch" href="/assets/js/29.17c547e6.js"><link rel="prefetch" href="/assets/js/3.8b254d5d.js"><link rel="prefetch" href="/assets/js/30.38bd809e.js"><link rel="prefetch" href="/assets/js/31.fbfb336c.js"><link rel="prefetch" href="/assets/js/32.591c3f2b.js"><link rel="prefetch" href="/assets/js/33.c456709f.js"><link rel="prefetch" href="/assets/js/34.5a071e36.js"><link rel="prefetch" href="/assets/js/36.144098aa.js"><link rel="prefetch" href="/assets/js/4.26a3069c.js"><link rel="prefetch" href="/assets/js/5.f92a6aca.js"><link rel="prefetch" href="/assets/js/6.ee5ffca3.js"><link rel="prefetch" href="/assets/js/7.6bf27a87.js"><link rel="prefetch" href="/assets/js/8.8b72a8d3.js"><link rel="prefetch" href="/assets/js/9.7919fc1d.js">
|
||||
<link rel="stylesheet" href="/assets/css/0.styles.a0ada997.css">
|
||||
</head>
|
||||
<body>
|
||||
<div id="app" data-server-rendered="true"><div class="theme-container"><header class="navbar"><div class="sidebar-button"><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" role="img" viewBox="0 0 448 512" class="icon"><path fill="currentColor" d="M436 124H12c-6.627 0-12-5.373-12-12V80c0-6.627 5.373-12 12-12h424c6.627 0 12 5.373 12 12v32c0 6.627-5.373 12-12 12zm0 160H12c-6.627 0-12-5.373-12-12v-32c0-6.627 5.373-12 12-12h424c6.627 0 12 5.373 12 12v32c0 6.627-5.373 12-12 12zm0 160H12c-6.627 0-12-5.373-12-12v-32c0-6.627 5.373-12 12-12h424c6.627 0 12 5.373 12 12v32c0 6.627-5.373 12-12 12z"></path></svg></div> <a href="/" class="home-link router-link-active"><!----> <span class="site-name">Flagger</span></a> <div class="links"><div class="search-box"><input aria-label="Search" autocomplete="off" spellcheck="false" value=""> <!----></div> <nav class="nav-links can-hide"><div class="nav-item"><a href="https://docs.flagger.app" target="_blank" rel="noopener noreferrer" class="nav-link external">
|
||||
Docs
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></div><div class="nav-item"><a href="https://github.com/weaveworks/flagger/blob/master/CHANGELOG.md" target="_blank" rel="noopener noreferrer" class="nav-link external">
|
||||
Changelog
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></div> <a href="https://github.com/weaveworks/flagger" target="_blank" rel="noopener noreferrer" class="repo-link">
|
||||
GitHub
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></nav></div></header> <div class="sidebar-mask"></div> <aside class="sidebar"><nav class="nav-links"><div class="nav-item"><a href="https://docs.flagger.app" target="_blank" rel="noopener noreferrer" class="nav-link external">
|
||||
Docs
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></div><div class="nav-item"><a href="https://github.com/weaveworks/flagger/blob/master/CHANGELOG.md" target="_blank" rel="noopener noreferrer" class="nav-link external">
|
||||
Changelog
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></div> <a href="https://github.com/weaveworks/flagger" target="_blank" rel="noopener noreferrer" class="repo-link">
|
||||
GitHub
|
||||
<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a></nav> <ul class="sidebar-links"><li><a href="/" class="sidebar-link">Home</a></li><li><section class="sidebar-group depth-0"><a href="/intro/" class="sidebar-heading clickable"><span>Introduction</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/intro/" class="sidebar-link">Get Started</a></li><li><a href="/intro/faq.html" class="sidebar-link">FAQ</a></li></ul></section></li><li><section class="sidebar-group depth-0"><a href="/install/flagger-install-on-kubernetes" class="sidebar-heading clickable"><span>Install</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/install/flagger-install-on-kubernetes.html" class="sidebar-link">On Kubernetes</a></li><li><a href="/install/flagger-install-on-google-cloud.html" class="sidebar-link">On GKE Istio</a></li><li><a href="/install/flagger-install-on-eks-appmesh.html" class="sidebar-link">On EKS App Mesh</a></li></ul></section></li><li><section class="sidebar-group depth-0"><a href="/usage/how-it-works" class="sidebar-heading clickable open"><span>Usage</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/usage/how-it-works.html" class="sidebar-link">How it works</a></li><li><a href="/usage/deployment-strategies.html" class="sidebar-link">Deployment Strategies</a></li><li><a href="/usage/metrics.html" class="sidebar-link">Metrics Analysis</a></li><li><a href="/usage/webhooks.html" class="active sidebar-link">Webhooks</a><ul class="sidebar-sub-headers"><li class="sidebar-sub-header"><a href="/usage/webhooks.html#load-testing" class="sidebar-link">Load Testing</a></li><li class="sidebar-sub-header"><a href="/usage/webhooks.html#load-testing-delegation" class="sidebar-link">Load Testing Delegation</a></li><li class="sidebar-sub-header"><a href="/usage/webhooks.html#integration-testing" class="sidebar-link">Integration Testing</a></li><li class="sidebar-sub-header"><a href="/usage/webhooks.html#manual-gating" class="sidebar-link">Manual Gating</a></li></ul></li><li><a href="/usage/alerting.html" class="sidebar-link">Alerting</a></li><li><a href="/usage/monitoring.html" class="sidebar-link">Monitoring</a></li></ul></section></li><li><section class="sidebar-group depth-0"><a href="/tutorials/istio-progressive-delivery" class="sidebar-heading clickable"><span>Tutorials</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/tutorials/istio-progressive-delivery.html" class="sidebar-link">Istio Canaries</a></li><li><a href="/tutorials/istio-ab-testing.html" class="sidebar-link">Istio A/B Testing</a></li><li><a href="/tutorials/linkerd-progressive-delivery.html" class="sidebar-link">Linkerd Canaries</a></li><li><a href="/tutorials/appmesh-progressive-delivery.html" class="sidebar-link">App Mesh Canaries</a></li><li><a href="/tutorials/nginx-progressive-delivery.html" class="sidebar-link">NGINX Ingress Canaries</a></li><li><a href="/tutorials/gloo-progressive-delivery.html" class="sidebar-link">Gloo Canaries</a></li><li><a href="/tutorials/contour-progressive-delivery.html" class="sidebar-link">Contour Canaries</a></li><li><a href="/tutorials/kubernetes-blue-green.html" class="sidebar-link">Kubernetes Blue/Green</a></li><li><a href="/tutorials/canary-helm-gitops.html" class="sidebar-link">Canaries with Helm charts and GitOps</a></li></ul></section></li><li><section class="sidebar-group depth-0"><a href="/dev/dev-guide" class="sidebar-heading clickable"><span>Dev</span> <!----></a> <ul class="sidebar-links sidebar-group-items"><li><a href="/dev/dev-guide.html" class="sidebar-link">Development Guide</a></li><li><a href="/dev/release-guide.html" class="sidebar-link">Release Guide</a></li><li><a href="/dev/upgrade-guide.html" class="sidebar-link">Upgrade Guide</a></li></ul></section></li></ul> </aside> <main class="page"> <div class="theme-default-content content__default"><h1 id="webhooks"><a href="#webhooks" aria-hidden="true" class="header-anchor">#</a> Webhooks</h1> <p>The canary analysis can be extended with webhooks. Flagger will call each webhook URL and
|
||||
determine from the response status code (HTTP 2xx) if the canary is failing or not.</p> <p>There are several types of hooks:</p> <ul><li><strong>confirm-rollout</strong> hooks are executed before scaling up the canary deployment and can be used for manual approval.
|
||||
The rollout is paused until the hook returns a successful HTTP status code.</li> <li><strong>pre-rollout</strong> hooks are executed before routing traffic to canary.
|
||||
The canary advancement is paused if a pre-rollout hook fails and if the number of failures reach the
|
||||
threshold the canary will be rollback.</li> <li><strong>rollout</strong> hooks are executed during the analysis on each iteration before the metric checks.
|
||||
If a rollout hook call fails the canary advancement is paused and eventfully rolled back.</li> <li><strong>confirm-promotion</strong> hooks are executed before the promotion step.
|
||||
The canary promotion is paused until the hooks return HTTP 200.
|
||||
While the promotion is paused, Flagger will continue to run the metrics checks and rollout hooks.</li> <li><strong>post-rollout</strong> hooks are executed after the canary has been promoted or rolled back.
|
||||
If a post rollout hook fails the error is logged.</li> <li><strong>rollback</strong> hooks are executed while a canary deployment is in either Progressing or Waiting status.
|
||||
This provides the ability to rollback during analysis or while waiting for a confirmation. If a rollback hook
|
||||
returns a successful HTTP status code, Flagger will stop the analysis and mark the canary release as failed.</li> <li><strong>event</strong> hooks are executed every time Flagger emits a Kubernetes event. When configured,
|
||||
every action that Flagger takes during a canary deployment will be sent as JSON via an HTTP POST request.</li></ul> <p>Spec:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code> <span class="token key atrule">analysis</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">webhooks</span><span class="token punctuation">:</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> <span class="token string">"start gate"</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> confirm<span class="token punctuation">-</span>rollout
|
||||
<span class="token key atrule">url</span><span class="token punctuation">:</span> http<span class="token punctuation">:</span>//flagger<span class="token punctuation">-</span>loadtester.test/gate/approve
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> <span class="token string">"helm test"</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> pre<span class="token punctuation">-</span>rollout
|
||||
<span class="token key atrule">url</span><span class="token punctuation">:</span> http<span class="token punctuation">:</span>//flagger<span class="token punctuation">-</span>helmtester.flagger/
|
||||
<span class="token key atrule">timeout</span><span class="token punctuation">:</span> 3m
|
||||
<span class="token key atrule">metadata</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> <span class="token string">"helmv3"</span>
|
||||
<span class="token key atrule">cmd</span><span class="token punctuation">:</span> <span class="token string">"test podinfo -n test"</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> <span class="token string">"load test"</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> rollout
|
||||
<span class="token key atrule">url</span><span class="token punctuation">:</span> http<span class="token punctuation">:</span>//flagger<span class="token punctuation">-</span>loadtester.test/
|
||||
<span class="token key atrule">timeout</span><span class="token punctuation">:</span> 15s
|
||||
<span class="token key atrule">metadata</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">cmd</span><span class="token punctuation">:</span> <span class="token string">"hey -z 1m -q 5 -c 2 http://podinfo-canary.test:9898/"</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> <span class="token string">"promotion gate"</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> confirm<span class="token punctuation">-</span>promotion
|
||||
<span class="token key atrule">url</span><span class="token punctuation">:</span> http<span class="token punctuation">:</span>//flagger<span class="token punctuation">-</span>loadtester.test/gate/approve
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> <span class="token string">"notify"</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> post<span class="token punctuation">-</span>rollout
|
||||
<span class="token key atrule">url</span><span class="token punctuation">:</span> http<span class="token punctuation">:</span>//telegram.bot<span class="token punctuation">:</span>8080/
|
||||
<span class="token key atrule">timeout</span><span class="token punctuation">:</span> 5s
|
||||
<span class="token key atrule">metadata</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">some</span><span class="token punctuation">:</span> <span class="token string">"message"</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> <span class="token string">"rollback gate"</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> rollback
|
||||
<span class="token key atrule">url</span><span class="token punctuation">:</span> http<span class="token punctuation">:</span>//flagger<span class="token punctuation">-</span>loadtester.test/rollback/check
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> <span class="token string">"send to Slack"</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> event
|
||||
<span class="token key atrule">url</span><span class="token punctuation">:</span> http<span class="token punctuation">:</span>//event<span class="token punctuation">-</span>recevier.notifications/slack
|
||||
</code></pre></div><blockquote><p><strong>Note</strong> that the sum of all rollout webhooks timeouts should be lower than the analysis interval.</p></blockquote> <p>Webhook payload (HTTP POST):</p> <div class="language-json extra-class"><pre class="language-json"><code><span class="token punctuation">{</span>
|
||||
<span class="token property">"name"</span><span class="token operator">:</span> <span class="token string">"podinfo"</span><span class="token punctuation">,</span>
|
||||
<span class="token property">"namespace"</span><span class="token operator">:</span> <span class="token string">"test"</span><span class="token punctuation">,</span>
|
||||
<span class="token property">"phase"</span><span class="token operator">:</span> <span class="token string">"Progressing"</span><span class="token punctuation">,</span>
|
||||
<span class="token property">"metadata"</span><span class="token operator">:</span> <span class="token punctuation">{</span>
|
||||
<span class="token property">"test"</span><span class="token operator">:</span> <span class="token string">"all"</span><span class="token punctuation">,</span>
|
||||
<span class="token property">"token"</span><span class="token operator">:</span> <span class="token string">"16688eb5e9f289f1991c"</span>
|
||||
<span class="token punctuation">}</span>
|
||||
<span class="token punctuation">}</span>
|
||||
</code></pre></div><p>Response status codes:</p> <ul><li>200-202 - advance canary by increasing the traffic weight</li> <li>timeout or non-2xx - halt advancement and increment failed checks</li></ul> <p>On a non-2xx response Flagger will include the response body (if any) in the failed checks log and Kubernetes events.</p> <p>Event payload (HTTP POST):</p> <div class="language-json extra-class"><pre class="language-json"><code><span class="token punctuation">{</span>
|
||||
<span class="token property">"name"</span><span class="token operator">:</span> <span class="token string">"string (canary name)"</span><span class="token punctuation">,</span>
|
||||
<span class="token property">"namespace"</span><span class="token operator">:</span> <span class="token string">"string (canary namespace)"</span><span class="token punctuation">,</span>
|
||||
<span class="token property">"phase"</span><span class="token operator">:</span> <span class="token string">"string (canary phase)"</span><span class="token punctuation">,</span>
|
||||
<span class="token property">"metadata"</span><span class="token operator">:</span> <span class="token punctuation">{</span>
|
||||
<span class="token property">"eventMessage"</span><span class="token operator">:</span> <span class="token string">"string (canary event message)"</span><span class="token punctuation">,</span>
|
||||
<span class="token property">"eventType"</span><span class="token operator">:</span> <span class="token string">"string (canary event type)"</span><span class="token punctuation">,</span>
|
||||
<span class="token property">"timestamp"</span><span class="token operator">:</span> <span class="token string">"string (unix timestamp ms)"</span>
|
||||
<span class="token punctuation">}</span>
|
||||
<span class="token punctuation">}</span>
|
||||
</code></pre></div><p>The event receiver can create alerts based on the received phase
|
||||
(possible values: <code>Initialized</code>, <code>Waiting</code>, <code>Progressing</code>, <code>Promoting</code>, <code>Finalising</code>, <code>Succeeded</code> or <code>Failed</code>).</p> <h2 id="load-testing"><a href="#load-testing" aria-hidden="true" class="header-anchor">#</a> Load Testing</h2> <p>For workloads that are not receiving constant traffic Flagger can be configured with a webhook,
|
||||
that when called, will start a load test for the target workload.
|
||||
If the target workload doesn't receive any traffic during the canary analysis,
|
||||
Flagger metric checks will fail with "no values found for metric request-success-rate".</p> <p>Flagger comes with a load testing service based on <a href="https://github.com/rakyll/hey" target="_blank" rel="noopener noreferrer">rakyll/hey<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a>
|
||||
that generates traffic during analysis when configured as a webhook.</p> <p><img src="https://raw.githubusercontent.com/weaveworks/flagger/master/docs/diagrams/flagger-load-testing.png" alt="Flagger Load Testing Webhook"></p> <p>First you need to deploy the load test runner in a namespace with sidecar injection enabled:</p> <div class="language-bash extra-class"><pre class="language-bash"><code>kubectl apply -k github.com/weaveworks/flagger//kustomize/tester
|
||||
</code></pre></div><p>Or by using Helm:</p> <div class="language-bash extra-class"><pre class="language-bash"><code>helm repo <span class="token function">add</span> flagger https://flagger.app
|
||||
|
||||
helm upgrade -i flagger-loadtester flagger/loadtester <span class="token punctuation">\</span>
|
||||
--namespace<span class="token operator">=</span>test <span class="token punctuation">\</span>
|
||||
--set cmd.timeout<span class="token operator">=</span>1h
|
||||
</code></pre></div><p>When deployed the load tester API will be available at <code>http://flagger-loadtester.test/</code>.</p> <p>Now you can add webhooks to the canary analysis spec:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code><span class="token key atrule">webhooks</span><span class="token punctuation">:</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> load<span class="token punctuation">-</span>test<span class="token punctuation">-</span>get
|
||||
<span class="token key atrule">url</span><span class="token punctuation">:</span> http<span class="token punctuation">:</span>//flagger<span class="token punctuation">-</span>loadtester.test/
|
||||
<span class="token key atrule">timeout</span><span class="token punctuation">:</span> 5s
|
||||
<span class="token key atrule">metadata</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> cmd
|
||||
<span class="token key atrule">cmd</span><span class="token punctuation">:</span> <span class="token string">"hey -z 1m -q 10 -c 2 http://podinfo-canary.test:9898/"</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> load<span class="token punctuation">-</span>test<span class="token punctuation">-</span>post
|
||||
<span class="token key atrule">url</span><span class="token punctuation">:</span> http<span class="token punctuation">:</span>//flagger<span class="token punctuation">-</span>loadtester.test/
|
||||
<span class="token key atrule">timeout</span><span class="token punctuation">:</span> 5s
|
||||
<span class="token key atrule">metadata</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> cmd
|
||||
<span class="token key atrule">cmd</span><span class="token punctuation">:</span> <span class="token string">"hey -z 1m -q 10 -c 2 -m POST -d '{test: 2}' http://podinfo-canary.test:9898/echo"</span>
|
||||
</code></pre></div><p>When the canary analysis starts, Flagger will call the webhooks and the load tester will run the <code>hey</code> commands
|
||||
in the background, if they are not already running. This will ensure that during the
|
||||
analysis, the <code>podinfo-canary.test</code> service will receive a steady stream of GET and POST requests.</p> <p>If your workload is exposed outside the mesh you can point <code>hey</code> to the
|
||||
public URL and use HTTP2.</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code><span class="token key atrule">webhooks</span><span class="token punctuation">:</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> load<span class="token punctuation">-</span>test<span class="token punctuation">-</span>get
|
||||
<span class="token key atrule">url</span><span class="token punctuation">:</span> http<span class="token punctuation">:</span>//flagger<span class="token punctuation">-</span>loadtester.test/
|
||||
<span class="token key atrule">timeout</span><span class="token punctuation">:</span> 5s
|
||||
<span class="token key atrule">metadata</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> cmd
|
||||
<span class="token key atrule">cmd</span><span class="token punctuation">:</span> <span class="token string">"hey -z 1m -q 10 -c 2 -h2 https://podinfo.example.com/"</span>
|
||||
</code></pre></div><p>For gRPC services you can use <a href="https://github.com/bojand/ghz" target="_blank" rel="noopener noreferrer">bojand/ghz<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a> which is a similar tool to Hey but for gPRC:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code><span class="token key atrule">webhooks</span><span class="token punctuation">:</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> grpc<span class="token punctuation">-</span>load<span class="token punctuation">-</span>test
|
||||
<span class="token key atrule">url</span><span class="token punctuation">:</span> http<span class="token punctuation">:</span>//flagger<span class="token punctuation">-</span>loadtester.test/
|
||||
<span class="token key atrule">timeout</span><span class="token punctuation">:</span> 5s
|
||||
<span class="token key atrule">metadata</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> cmd
|
||||
<span class="token key atrule">cmd</span><span class="token punctuation">:</span> <span class="token string">"ghz -z 1m -q 10 -c 2 --insecure podinfo.test:9898"</span>
|
||||
</code></pre></div><p><code>ghz</code> uses reflection to identify which gRPC method to call. If you do not wish to enable reflection for your gRPC service you can implement a standardized health check from the <a href="https://github.com/grpc/grpc-proto" target="_blank" rel="noopener noreferrer">grpc-proto<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a> library. To use this <a href="https://github.com/grpc/grpc-proto/blob/master/grpc/health/v1/health.proto" target="_blank" rel="noopener noreferrer">health check schema<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a> without reflection you can pass a parameter to <code>ghz</code> like this</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code><span class="token key atrule">webhooks</span><span class="token punctuation">:</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> grpc<span class="token punctuation">-</span>load<span class="token punctuation">-</span>test<span class="token punctuation">-</span>no<span class="token punctuation">-</span>reflection
|
||||
<span class="token key atrule">url</span><span class="token punctuation">:</span> http<span class="token punctuation">:</span>//flagger<span class="token punctuation">-</span>loadtester.test/
|
||||
<span class="token key atrule">timeout</span><span class="token punctuation">:</span> 5s
|
||||
<span class="token key atrule">metadata</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> cmd
|
||||
<span class="token key atrule">cmd</span><span class="token punctuation">:</span> <span class="token string">"ghz --insecure --proto=/tmp/ghz/health.proto --call=grpc.health.v1.Health/Check podinfo.test:9898"</span>
|
||||
</code></pre></div><p>The load tester can run arbitrary commands as long as the binary is present in the container image.
|
||||
For example if you you want to replace <code>hey</code> with another CLI, you can create your own Docker image:</p> <div class="language-dockerfile extra-class"><pre class="language-text"><code>FROM weaveworks/flagger-loadtester:<VER>
|
||||
|
||||
RUN curl -Lo /usr/local/bin/my-cli https://github.com/user/repo/releases/download/ver/my-cli \
|
||||
&& chmod +x /usr/local/bin/my-cli
|
||||
</code></pre></div><h2 id="load-testing-delegation"><a href="#load-testing-delegation" aria-hidden="true" class="header-anchor">#</a> Load Testing Delegation</h2> <p>The load tester can also forward testing tasks to external tools, by now <a href="https://github.com/naver/ngrinder" target="_blank" rel="noopener noreferrer">nGrinder<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a>
|
||||
is supported.</p> <p>To use this feature, add a load test task of type 'ngrinder' to the canary analysis spec:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code><span class="token key atrule">webhooks</span><span class="token punctuation">:</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> load<span class="token punctuation">-</span>test<span class="token punctuation">-</span>post
|
||||
<span class="token key atrule">url</span><span class="token punctuation">:</span> http<span class="token punctuation">:</span>//flagger<span class="token punctuation">-</span>loadtester.test/
|
||||
<span class="token key atrule">timeout</span><span class="token punctuation">:</span> 5s
|
||||
<span class="token key atrule">metadata</span><span class="token punctuation">:</span>
|
||||
<span class="token comment"># type of this load test task, cmd or ngrinder</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> ngrinder
|
||||
<span class="token comment"># base url of your nGrinder controller server</span>
|
||||
<span class="token key atrule">server</span><span class="token punctuation">:</span> http<span class="token punctuation">:</span>//ngrinder<span class="token punctuation">-</span>server<span class="token punctuation">:</span>port
|
||||
<span class="token comment"># id of the test to clone from, the test must have been defined.</span>
|
||||
<span class="token key atrule">clone</span><span class="token punctuation">:</span> <span class="token number">100</span>
|
||||
<span class="token comment"># user name and base64 encoded password to authenticate against the nGrinder server</span>
|
||||
<span class="token key atrule">username</span><span class="token punctuation">:</span> admin
|
||||
<span class="token key atrule">passwd</span><span class="token punctuation">:</span> YWRtaW4=
|
||||
<span class="token comment"># the interval between between nGrinder test status polling, default to 1s</span>
|
||||
<span class="token key atrule">pollInterval</span><span class="token punctuation">:</span> 5s
|
||||
</code></pre></div><p>When the canary analysis starts, the load tester will initiate a <a href="https://github.com/naver/ngrinder/wiki/REST-API-PerfTest" target="_blank" rel="noopener noreferrer">clone_and_start request<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a>
|
||||
to the nGrinder server and start a new performance test. the load tester will periodically poll the nGrinder server
|
||||
for the status of the test, and prevent duplicate requests from being sent in subsequent analysis loops.</p> <h2 id="integration-testing"><a href="#integration-testing" aria-hidden="true" class="header-anchor">#</a> Integration Testing</h2> <p>Flagger comes with a testing service that can run Helm tests or Bats tests when configured as a webhook.</p> <p>Deploy the Helm test runner in the <code>kube-system</code> namespace using the <code>tiller</code> service account:</p> <div class="language-bash extra-class"><pre class="language-bash"><code>helm repo <span class="token function">add</span> flagger https://flagger.app
|
||||
|
||||
helm upgrade -i flagger-helmtester flagger/loadtester <span class="token punctuation">\</span>
|
||||
--namespace<span class="token operator">=</span>kube-system <span class="token punctuation">\</span>
|
||||
--set <span class="token assign-left variable">serviceAccountName</span><span class="token operator">=</span>tiller
|
||||
</code></pre></div><p>When deployed the Helm tester API will be available at <code>http://flagger-helmtester.kube-system/</code>.</p> <p>Now you can add pre-rollout webhooks to the canary analysis spec:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code> <span class="token key atrule">analysis</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">webhooks</span><span class="token punctuation">:</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> <span class="token string">"smoke test"</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> pre<span class="token punctuation">-</span>rollout
|
||||
<span class="token key atrule">url</span><span class="token punctuation">:</span> http<span class="token punctuation">:</span>//flagger<span class="token punctuation">-</span>helmtester.kube<span class="token punctuation">-</span>system/
|
||||
<span class="token key atrule">timeout</span><span class="token punctuation">:</span> 3m
|
||||
<span class="token key atrule">metadata</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> <span class="token string">"helm"</span>
|
||||
<span class="token key atrule">cmd</span><span class="token punctuation">:</span> <span class="token string">"test {{ .Release.Name }} --cleanup"</span>
|
||||
</code></pre></div><p>When the canary analysis starts, Flagger will call the pre-rollout webhooks before routing traffic to the canary.
|
||||
If the helm test fails, Flagger will retry until the analysis threshold is reached and the canary is rolled back.</p> <p>If you are using Helm v3, you'll have to create a dedicated service account and add the release namespace to the test command:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code> <span class="token key atrule">analysis</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">webhooks</span><span class="token punctuation">:</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> <span class="token string">"smoke test"</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> pre<span class="token punctuation">-</span>rollout
|
||||
<span class="token key atrule">url</span><span class="token punctuation">:</span> http<span class="token punctuation">:</span>//flagger<span class="token punctuation">-</span>helmtester.kube<span class="token punctuation">-</span>system/
|
||||
<span class="token key atrule">timeout</span><span class="token punctuation">:</span> 3m
|
||||
<span class="token key atrule">metadata</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> <span class="token string">"helmv3"</span>
|
||||
<span class="token key atrule">cmd</span><span class="token punctuation">:</span> <span class="token string">"test {{ .Release.Name }} --timeout 3m -n {{ .Release.Namespace }}"</span>
|
||||
</code></pre></div><p>As an alternative to Helm you can use the <a href="https://github.com/bats-core/bats-core" target="_blank" rel="noopener noreferrer">Bash Automated Testing System<svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg></a> to run your tests.</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code> <span class="token key atrule">analysis</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">webhooks</span><span class="token punctuation">:</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> <span class="token string">"acceptance tests"</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> pre<span class="token punctuation">-</span>rollout
|
||||
<span class="token key atrule">url</span><span class="token punctuation">:</span> http<span class="token punctuation">:</span>//flagger<span class="token punctuation">-</span>batstester.default/
|
||||
<span class="token key atrule">timeout</span><span class="token punctuation">:</span> 5m
|
||||
<span class="token key atrule">metadata</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> <span class="token string">"bash"</span>
|
||||
<span class="token key atrule">cmd</span><span class="token punctuation">:</span> <span class="token string">"bats /tests/acceptance.bats"</span>
|
||||
</code></pre></div><p>Note that you should create a ConfigMap with your Bats tests and mount it inside the tester container.</p> <h2 id="manual-gating"><a href="#manual-gating" aria-hidden="true" class="header-anchor">#</a> Manual Gating</h2> <p>For manual approval of a canary deployment you can use the <code>confirm-rollout</code> and <code>confirm-promotion</code> webhooks.
|
||||
The confirmation rollout hooks are executed before the pre-rollout hooks.
|
||||
Flagger will halt the canary traffic shifting and analysis until the confirm webhook returns HTTP status 200.</p> <p>For manual rollback of a canary deployment you can use the <code>rollback</code> webhook. The rollback hook will be called
|
||||
during the analysis and confirmation states. If a rollback webhook returns a successful HTTP status code, Flagger
|
||||
will shift all traffic back to the primary instance and fail the canary.</p> <p>Manual gating with Flagger's tester:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code> <span class="token key atrule">analysis</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">webhooks</span><span class="token punctuation">:</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> <span class="token string">"gate"</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> confirm<span class="token punctuation">-</span>rollout
|
||||
<span class="token key atrule">url</span><span class="token punctuation">:</span> http<span class="token punctuation">:</span>//flagger<span class="token punctuation">-</span>loadtester.test/gate/halt
|
||||
</code></pre></div><p>The <code>/gate/halt</code> returns HTTP 403 thus blocking the rollout.</p> <p>If you have notifications enabled, Flagger will post a message to Slack or MS Teams if a canary rollout is waiting for approval.</p> <p>Change the URL to <code>/gate/approve</code> to start the canary analysis:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code> <span class="token key atrule">analysis</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">webhooks</span><span class="token punctuation">:</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> <span class="token string">"gate"</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> confirm<span class="token punctuation">-</span>rollout
|
||||
<span class="token key atrule">url</span><span class="token punctuation">:</span> http<span class="token punctuation">:</span>//flagger<span class="token punctuation">-</span>loadtester.test/gate/approve
|
||||
</code></pre></div><p>Manual gating can be driven with Flagger's tester API. Set the confirmation URL to <code>/gate/check</code>:</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code> <span class="token key atrule">analysis</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">webhooks</span><span class="token punctuation">:</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> <span class="token string">"ask for confirmation"</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> confirm<span class="token punctuation">-</span>rollout
|
||||
<span class="token key atrule">url</span><span class="token punctuation">:</span> http<span class="token punctuation">:</span>//flagger<span class="token punctuation">-</span>loadtester.test/gate/check
|
||||
</code></pre></div><p>By default the gate is closed, you can start or resume the canary rollout with:</p> <div class="language-bash extra-class"><pre class="language-bash"><code>kubectl -n <span class="token builtin class-name">test</span> <span class="token builtin class-name">exec</span> -it flagger-loadtester-xxxx-xxxx <span class="token function">sh</span>
|
||||
|
||||
<span class="token function">curl</span> -d <span class="token string">'{"name": "podinfo","namespace":"test"}'</span> http://localhost:8080/gate/open
|
||||
</code></pre></div><p>You can pause the rollout at any time with:</p> <div class="language-bash extra-class"><pre class="language-bash"><code><span class="token function">curl</span> -d <span class="token string">'{"name": "podinfo","namespace":"test"}'</span> http://localhost:8080/gate/close
|
||||
</code></pre></div><p>If a canary analysis is paused the status will change to waiting:</p> <div class="language-bash extra-class"><pre class="language-bash"><code>kubectl get canary/podinfo
|
||||
|
||||
NAME STATUS WEIGHT
|
||||
podinfo Waiting <span class="token number">0</span>
|
||||
</code></pre></div><p>The <code>confirm-promotion</code> hook type can be used to manually approve the canary promotion.
|
||||
While the promotion is paused, Flagger will continue to run the metrics checks and load tests.</p> <div class="language-yaml extra-class"><pre class="language-yaml"><code> <span class="token key atrule">analysis</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">webhooks</span><span class="token punctuation">:</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> <span class="token string">"promotion gate"</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> confirm<span class="token punctuation">-</span>promotion
|
||||
<span class="token key atrule">url</span><span class="token punctuation">:</span> http<span class="token punctuation">:</span>//flagger<span class="token punctuation">-</span>loadtester.test/gate/halt
|
||||
</code></pre></div><p>The <code>rollback</code> hook type can be used to manually rollback the canary promotion. As with gating, rollbacks can be driven
|
||||
with Flagger's tester API by setting the rollback URL to <code>/rollback/check</code></p> <div class="language-yaml extra-class"><pre class="language-yaml"><code> <span class="token key atrule">analysis</span><span class="token punctuation">:</span>
|
||||
<span class="token key atrule">webhooks</span><span class="token punctuation">:</span>
|
||||
<span class="token punctuation">-</span> <span class="token key atrule">name</span><span class="token punctuation">:</span> <span class="token string">"rollback"</span>
|
||||
<span class="token key atrule">type</span><span class="token punctuation">:</span> rollback
|
||||
<span class="token key atrule">url</span><span class="token punctuation">:</span> http<span class="token punctuation">:</span>//flagger<span class="token punctuation">-</span>loadtester.test/rollback/check
|
||||
</code></pre></div><p>By default rollback is closed, you can rollback a canary rollout with:</p> <div class="language-bash extra-class"><pre class="language-bash"><code>kubectl -n <span class="token builtin class-name">test</span> <span class="token builtin class-name">exec</span> -it flagger-loadtester-xxxx-xxxx <span class="token function">sh</span>
|
||||
|
||||
<span class="token function">curl</span> -d <span class="token string">'{"name": "podinfo","namespace":"test"}'</span> http://localhost:8080/rollback/open
|
||||
</code></pre></div><p>You can close the rollback with:</p> <div class="language-bash extra-class"><pre class="language-bash"><code><span class="token function">curl</span> -d <span class="token string">'{"name": "podinfo","namespace":"test"}'</span> http://localhost:8080/rollback/close
|
||||
</code></pre></div><p>If you have notifications enabled, Flagger will post a message to Slack or MS Teams if a canary has been rolled back.</p></div> <footer class="page-edit"><!----> <!----></footer> <div class="page-nav"><p class="inner"><span class="prev">
|
||||
←
|
||||
<a href="/usage/metrics.html" class="prev">
|
||||
Metrics Analysis
|
||||
</a></span> <span class="next"><a href="/usage/alerting.html">
|
||||
Alerting
|
||||
</a>
|
||||
→
|
||||
</span></p></div> </main></div><div class="global-ui"></div></div>
|
||||
<script src="/assets/js/app.b4b27991.js" defer></script><script src="/assets/js/2.ba5bf77c.js" defer></script><script src="/assets/js/35.fc27c09e.js" defer></script>
|
||||
</body>
|
||||
</html>
|
||||
Reference in New Issue
Block a user