<?xml version="1.0" encoding="utf-8" standalone="yes"?><rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom"><channel><title>Hubble on Zwindler's Reflection</title><link>https://blog.zwindler.fr/tags/hubble/</link><description>Recent content in Hubble on Zwindler's Reflection</description><generator>Hugo -- gohugo.io</generator><language>fr-fr</language><copyright>Licensed under CC BY-SA 4.0</copyright><lastBuildDate>Mon, 03 Nov 2025 12:00:00 +0200</lastBuildDate><atom:link href="https://blog.zwindler.fr/tags/hubble/index.xml" rel="self" type="application/rss+xml"/><item><title>Un nouveau champ `log` pour les network policies Cilium : une idée de use case</title><link>https://blog.zwindler.fr/2025/11/03/cilium-policy-log-field-limitation-fr/</link><pubDate>Mon, 03 Nov 2025 12:00:00 +0200</pubDate><guid>https://blog.zwindler.fr/2025/11/03/cilium-policy-log-field-limitation-fr/</guid><description>&lt;img src="https://blog.zwindler.fr/2025/10/cilium-hubble.webp" alt="Featured image of post Un nouveau champ `log` pour les network policies Cilium : une idée de use case" /&gt;&lt;h2 id="tldr"&gt;TL;DR
&lt;/h2&gt;&lt;p&gt;Cilium 1.18 a ajouté un champ &lt;code&gt;log&lt;/code&gt; aux CiliumNetworkPolicies pour taguer les verdicts de flux (FORWARDED, DROPPED, AUDIT, &amp;hellip;) avec des labels personnalisés. Dans l&amp;rsquo;idée, c&amp;rsquo;est la fonctionnalité parfaite pour éviter de logger le trafic bloqué que l&amp;rsquo;on connait dans nos dashboards de monitoring !&lt;/p&gt;
&lt;p&gt;Mais il y a un hic, sans rapport avec cette fonctionnalité, qui rend cette idée inutilisable : on ne peut pas l&amp;rsquo;utiliser avec &lt;code&gt;egressDeny&lt;/code&gt; + &lt;code&gt;toFQDNs&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;ET, il y a un bug, qui fait que le &amp;ldquo;log&amp;rdquo; n&amp;rsquo;est visible que sur le trafic &amp;ldquo;autorisé&amp;rdquo;.&lt;/p&gt;
&lt;p&gt;Je vous raconte&amp;hellip;&lt;/p&gt;
&lt;h2 id="le-problème--monitor-all-the-things-mais-pas-trop"&gt;Le problème : monitor all the things (mais pas trop)
&lt;/h2&gt;&lt;p&gt;Comme toute bonne équipe &amp;ldquo;ops&amp;rdquo; qui se respecte, nous monitorons/loggons les flux réseau de notre cluster Kubernetes avec Hubble pour une analyse ultérieure et de l&amp;rsquo;alerting. Nous (en particulier mon collègue Nicolas Nativel) poussons tous les flux &lt;code&gt;AUDIT&lt;/code&gt; et &lt;code&gt;DROPPED&lt;/code&gt; vers un dashboard Grafana pour pouvoir rapidement repérer quand quelque chose est bloqué et décider :&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;C&amp;rsquo;est légitime ? → On ouvre le flux&lt;/li&gt;
&lt;li&gt;C&amp;rsquo;est suspect ? → On déclenche l&amp;rsquo;alarme 🚨&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;img src="https://blog.zwindler.fr/2025/10/cilium-hubble.avif"
loading="lazy"
&gt;&lt;/p&gt;
&lt;p&gt;Ça fonctionne plutôt bien&amp;hellip; jusqu&amp;rsquo;à ce qu&amp;rsquo;on commence à bloquer &lt;strong&gt;explicitement&lt;/strong&gt; des choses qu&amp;rsquo;on &lt;em&gt;sait&lt;/em&gt; devoir être bloquées.&lt;/p&gt;
&lt;p&gt;Dans notre cas, nous voulions empêcher une application tierce d&amp;rsquo;envoyer les données de &amp;ldquo;télémétrie&amp;rdquo; (ouais, appelons ça comme ça 😏). On parle d&amp;rsquo;appels HTTPS vers des domaines de tracking externes.&lt;/p&gt;
&lt;p&gt;Le problème ? Si on bloque simplement ces flux, ils apparaîtront comme &lt;code&gt;DROPPED&lt;/code&gt; dans Hubble, déclencheront notre monitoring, et on se retrouvera avec des alertes pour quelque chose qu&amp;rsquo;on a &lt;em&gt;intentionnellement&lt;/em&gt; bloqué.&lt;/p&gt;
&lt;p&gt;C&amp;rsquo;est du bruit dont on ne veut pas.&lt;/p&gt;
&lt;h2 id="et-donc-ce-champ-log-des-network-policies-de-cilium-118-"&gt;Et donc, ce champ log des network policies de Cilium 1.18 ?
&lt;/h2&gt;&lt;p&gt;Bonne nouvelle ! Cilium 1.18 a introduit exactement ce dont nous avions besoin : la possibilité d&amp;rsquo;ajouter des champs de log personnalisés aux verdicts sur les network policies.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Cf. &lt;a class="link" href="https://isovalent.com/blog/post/cilium-1-18/#hubble-flow-policy-log-field" target="_blank" rel="noopener"
&gt;l&amp;rsquo;annonce dans le blogpost officiel&lt;/a&gt;.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;L&amp;rsquo;idée est simple : vous ajoutez un champ &lt;code&gt;log.value&lt;/code&gt; à votre CiliumNetworkPolicy :&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-yaml" data-lang="yaml"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nt"&gt;apiVersion&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;cilium.io/v2&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nt"&gt;kind&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;CiliumNetworkPolicy&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nt"&gt;metadata&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;my-policy&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nt"&gt;spec&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;endpointSelector&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;matchLabels&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;app&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;my-app&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;egress&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;- &lt;span class="nt"&gt;toFQDNs&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;- &lt;span class="nt"&gt;matchName&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;&amp;#34;example.com&amp;#34;&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;log&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;&amp;#34;my-custom-log-tag&amp;#34;&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Ensuite, quand vous observez les flux dans Hubble, vous pouvez &lt;strong&gt;les filtrer&lt;/strong&gt; en utilisant &lt;a class="link" href="https://kubernetes.io/docs/reference/using-api/cel/" target="_blank" rel="noopener"
&gt;CEL (Common Expression Language)&lt;/a&gt; :&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-bash" data-lang="bash"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;hubble observe &lt;span class="se"&gt;\
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt; --verdict AUDIT &lt;span class="se"&gt;\
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt; --not &lt;span class="se"&gt;\
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt; --cel-expression &lt;span class="s2"&gt;&amp;#34;(_flow.policy_log.endsWith(&amp;#39;my-custom-log-tag&amp;#39;))&amp;#34;&lt;/span&gt; &lt;span class="se"&gt;\
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt; --print-raw-filters
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Output :&lt;/p&gt;
&lt;pre tabindex="0"&gt;&lt;code&gt;allowlist:
- &amp;#39;{&amp;#34;verdict&amp;#34;:[&amp;#34;AUDIT&amp;#34;]}&amp;#39;
denylist:
- &amp;#39;{&amp;#34;experimental&amp;#34;:{&amp;#34;cel_expression&amp;#34;:[&amp;#34;(_flow.policy_log.endsWith(&amp;#39;&amp;#39;my-custom-log-tag&amp;#39;&amp;#39;))&amp;#34;]}}&amp;#39;
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;Parfait ! Vous savez maintenant taguer les calls que vous avez explicitement bloqués et les exclure de votre monitoring. 🎉&lt;/p&gt;
&lt;h2 id="le-plan--bloquer-la-télémétrie-élégamment"&gt;Le plan : bloquer la télémétrie élégamment
&lt;/h2&gt;&lt;p&gt;À l&amp;rsquo;aide de cette nouvelle fonctionnalité, nous avons élaboré notre stratégie :&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;Utiliser &lt;code&gt;egressDeny&lt;/code&gt; pour bloquer explicitement les domaines de télémétrie&lt;/li&gt;
&lt;li&gt;Ajouter un champ de log personnalisé : &lt;code&gt;app-explicit-traffic-blocked&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;Configurer Hubble pour filtrer les verdicts de flux avec ce tag&lt;/li&gt;
&lt;li&gt;Profit ! 🎉&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;Voici ce que nous avons essayé :&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-yaml" data-lang="yaml"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nt"&gt;apiVersion&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;cilium.io/v2&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nt"&gt;kind&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;CiliumNetworkPolicy&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nt"&gt;metadata&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;app-external-block-policy&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;namespace&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;my-namespace&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nt"&gt;spec&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;endpointSelector&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;matchLabels&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;app.kubernetes.io/name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;my-app&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="c"&gt;# note: egressDeny prend la précédence sur les règles egress&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="c"&gt;# https://docs.cilium.io/en/stable/security/policy/language/#deny-policies&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;egressDeny&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="c"&gt;# Bloquer tout le trafic externe et le logger avec un champ de log arbitraire&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="c"&gt;# Ceci est utilisé pour empêcher l&amp;#39;app d&amp;#39;envoyer des données de télémétrie à l&amp;#39;extérieur&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="c"&gt;# sans déclencher d&amp;#39;alerte AUDIT/DROPPED&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="c"&gt;# fonctionnalité ajoutée dans cilium 1.18.0 https://github.com/cilium/cilium/pull/39902&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;- &lt;span class="nt"&gt;toFQDNs&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;- &lt;span class="nt"&gt;matchPattern&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;&amp;#34;*.telemetry.example.com&amp;#34;&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;toPorts&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;- &lt;span class="nt"&gt;ports&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;- &lt;span class="nt"&gt;port&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;&amp;#34;443&amp;#34;&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;protocol&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;TCP&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;- &lt;span class="nt"&gt;port&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;&amp;#34;80&amp;#34;&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;protocol&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="l"&gt;TCP&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;log&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;&amp;#34;app-explicit-traffic-blocked&amp;#34;&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Ça devrait fonctionner, non ? On utilise &lt;code&gt;egressDeny&lt;/code&gt; (qui &lt;a class="link" href="https://docs.cilium.io/en/stable/security/policy/language/#deny-policies" target="_blank" rel="noopener"
&gt;prend la précédence sur les autres règles&lt;/a&gt;, ce qui est une bonne chose !), et on le tague avec notre log personnalisé.&lt;/p&gt;
&lt;h2 id="retour-à-la-réalité"&gt;Retour à la réalité
&lt;/h2&gt;&lt;p&gt;Et puis&amp;hellip; &lt;strong&gt;patatra&lt;/strong&gt;.&lt;/p&gt;
&lt;p&gt;En lisant la &lt;a class="link" href="https://docs.cilium.io/en/stable/security/policy/language/#deny-policies" target="_blank" rel="noopener"
&gt;documentation Cilium sur les deny policies&lt;/a&gt;, nous sommes tombés sur cette petite note de rien du tout :&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;Deny policies do not support:&lt;/strong&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;policy enforcement at L7, i.e., specifically denying an URL&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;toFQDNs&lt;/strong&gt;, i.e., specifically denying traffic to a specific domain name.&lt;/li&gt;
&lt;/ul&gt;
&lt;/blockquote&gt;
&lt;p&gt;Attendez, quoi ?&lt;/p&gt;
&lt;p&gt;On &lt;strong&gt;ne peut pas&lt;/strong&gt; utiliser &lt;code&gt;toFQDNs&lt;/code&gt; avec &lt;code&gt;egressDeny&lt;/code&gt;. Tout notre plan vient de s&amp;rsquo;effondrer 😱.&lt;/p&gt;
&lt;h2 id="pourquoi-cest-un-problème-déjà-"&gt;Pourquoi c&amp;rsquo;est un problème, déjà ?
&lt;/h2&gt;&lt;p&gt;Le problème, c&amp;rsquo;est le modèle de précédence dans Cilium :&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Les règles &lt;code&gt;egressDeny&lt;/code&gt; prennent la précédence sur les règles &lt;code&gt;egress&lt;/code&gt; (by design, et c&amp;rsquo;est bien !)&lt;/li&gt;
&lt;li&gt;Mais si on utilise &lt;code&gt;egressDeny&lt;/code&gt;, on ne peut pas utiliser &lt;code&gt;toFQDNs&lt;/code&gt; pour cibler intelligemment le domaine incriminé, on doit bloquer par IP ou CIDR&lt;/li&gt;
&lt;li&gt;Ces services de télémétrie utilisent &lt;em&gt;probablement&lt;/em&gt; des IPs dynamiques pour leurs endpoints (bonne chance pour maintenir une liste&amp;hellip;)&lt;/li&gt;
&lt;li&gt;Et si on bloque tout le trafic 80/443 dans &lt;code&gt;egressDeny&lt;/code&gt;, on ne peut pas faire d&amp;rsquo;exceptions pour le trafic légitime dans les règles &lt;code&gt;egress&lt;/code&gt; car&amp;hellip; &lt;em&gt;deny&lt;/em&gt; prend la précédence sur &lt;em&gt;allow&lt;/em&gt; !&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;On est coincé entre le marteau et l&amp;rsquo;enclume :&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Utiliser &lt;code&gt;egress&lt;/code&gt; avec &lt;code&gt;toFQDNs&lt;/code&gt; → ça marche, mais on ne peut pas &lt;strong&gt;bloquer&lt;/strong&gt;, seulement autoriser&lt;/li&gt;
&lt;li&gt;Utiliser &lt;code&gt;egressDeny&lt;/code&gt; avec des IPs → on va jouer au chat et à la souris avec des plages IP qui changent&lt;/li&gt;
&lt;li&gt;Utiliser &lt;code&gt;egressDeny&lt;/code&gt; pour bloquer tout le 80/443 → on bloque tout, y compris le trafic légitime&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id="solutions-de-contournement-potentielles"&gt;Solutions de contournement potentielles
&lt;/h2&gt;&lt;p&gt;En attendant que Cilium supporte &lt;code&gt;toFQDNs&lt;/code&gt; dans les policies &lt;code&gt;egressDeny&lt;/code&gt;, voici quelques approches alternatives que vous pourriez envisager :&lt;/p&gt;
&lt;h3 id="trouver-un-moyen-de-désactiver-la-télémétrie-directement-dans-lapp"&gt;Trouver un moyen de désactiver la télémétrie directement dans l&amp;rsquo;app
&lt;/h3&gt;&lt;p&gt;C&amp;rsquo;est la meilleure option, mais malheureusement pas toujours sur la table.&lt;/p&gt;
&lt;h3 id="blocage-basé-sur-le-dns"&gt;Blocage basé sur le DNS
&lt;/h3&gt;&lt;p&gt;Configurer le serveur DNS pour retourner NXDOMAIN pour les domaines de télémétrie, comme un serveur &lt;a class="link" href="https://pi-hole.net/" target="_blank" rel="noopener"
&gt;pi-hole&lt;/a&gt; personnel le ferait avec les pubs. L&amp;rsquo;application échouera à résoudre le domaine et n&amp;rsquo;enverra pas de données.&lt;/p&gt;
&lt;h3 id="utiliser-egressdeny-basé-sur-les-ips-avec-un-overhead-de-maintenance"&gt;Utiliser egressDeny basé sur les IPs (avec un overhead de maintenance)
&lt;/h3&gt;&lt;p&gt;Résoudre les FQDNs de télémétrie vers leurs plages IP actuelles et les bloquer avec &lt;code&gt;egressDeny&lt;/code&gt; :&lt;/p&gt;
&lt;div class="highlight"&gt;&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-yaml" data-lang="yaml"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="nt"&gt;egressDeny&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;- &lt;span class="nt"&gt;toCIDRSet&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;- &lt;span class="nt"&gt;cidr&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="m"&gt;203.0.113.0&lt;/span&gt;&lt;span class="l"&gt;/24 &lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="c"&gt;# Exemple de plage IP de télémétrie&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nt"&gt;toPorts&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;- &lt;span class="nt"&gt;ports&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt; &lt;/span&gt;- &lt;span class="nt"&gt;port&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;&amp;#34;443&amp;#34;&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;Si la liste n&amp;rsquo;évolue pas trop souvent, c&amp;rsquo;est une bonne option.&lt;/p&gt;
&lt;h2 id="ok-mais-imaginons-quil-ny-ait-pas-de-trafic-légitime-peut-on-utiliser-la-fonctionnalité-pour-ajouter-un-log-sur-le-trafic-droppé-"&gt;OK, mais imaginons qu&amp;rsquo;il n&amp;rsquo;y ait pas de trafic légitime. Peut-on utiliser la fonctionnalité pour ajouter un log sur le trafic droppé ?
&lt;/h2&gt;&lt;p&gt;&lt;strong&gt;Malheureusement non, pas pour le moment.&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;Il y a un bug dans cette nouvelle fonctionnalité de Cilium qui ne log le champ &lt;code&gt;policy_log&lt;/code&gt; que sur les flux &amp;ldquo;autorisés&amp;rdquo;, pas sur les flux audit/dropped.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a class="link" href="https://github.com/cilium/cilium/issues/42044" target="_blank" rel="noopener"
&gt;Policy log does not work for DROPPED/AUDIT flow&lt;/a&gt; ouverte par mon collègue Nicolas :&lt;/li&gt;
&lt;/ul&gt;
&lt;blockquote&gt;
&lt;p&gt;When defining a CiliumNetworkPolicy with the spec.log field configured, I expect the relevant hubble flows to have the policy_log field. It works for allowed flow.&lt;/p&gt;
&lt;p&gt;But for denied/audited flow resulting from the rule (implicit or explicit), policy_log is never available.&lt;/p&gt;
&lt;p&gt;Note: I observe the same issue with &lt;code&gt;--print-policy-names&lt;/code&gt; option of hubble, the k8s:io.cilium.k8s.policy.derived-from label is not set for denied flows (but correctly set for allowed flows).&lt;/p&gt;
&lt;/blockquote&gt;
&lt;ul&gt;
&lt;li&gt;et une autre issue &lt;a class="link" href="https://github.com/cilium/cilium/issues/41912" target="_blank" rel="noopener"
&gt;[Hubble CLI] &amp;ndash;print-policy-names flag does not do anything&lt;/a&gt; ouverte par quelqu&amp;rsquo;un d&amp;rsquo;autre.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Puisque 2 tickets sont ouverts et que les mainteneurs ont commencé à répondre dessus, on peut espérer que ce soit corrigé un jour.&lt;/p&gt;
&lt;h2 id="conclusion"&gt;Conclusion
&lt;/h2&gt;&lt;p&gt;Dans notre cas d&amp;rsquo;usage, nous n&amp;rsquo;avons finalement pas utilisé cette nouvelle fonctionnalité de Cilium. Mais donner la possibilité d&amp;rsquo;ajouter des détails (et permettre de filtrer dessus également) est toujours une feature sympa.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Un grand merci à mon collègue Nicolas Nativel, qui a fait la majorité du travail autour des CiliumNetworkPolicies, incluant les dashboards, le travail exploratoire sur cette fonctionnalité, et a pris le temps de créer l&amp;rsquo;issue sur le repo Cilium.&lt;/strong&gt;&lt;/p&gt;
&lt;h2 id="références"&gt;Références
&lt;/h2&gt;&lt;ul&gt;
&lt;li&gt;&lt;a class="link" href="https://isovalent.com/blog/post/cilium-1-18/#hubble-flow-policy-log-field" target="_blank" rel="noopener"
&gt;Blogpost officiel pour la sortie de Cilium 1.18 - Hubble flow policy log field&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a class="link" href="https://www.danielstechblog.io/ciliums-new-hubble-flow-policy-log-field/" target="_blank" rel="noopener"
&gt;Daniel&amp;rsquo;s Tech Blog - Cilium&amp;rsquo;s new Hubble flow policy log field&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a class="link" href="https://docs.cilium.io/en/stable/security/policy/language/#deny-policies" target="_blank" rel="noopener"
&gt;Docs Cilium - Deny Policies&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a class="link" href="https://github.com/cilium/cilium/pull/39902" target="_blank" rel="noopener"
&gt;GitHub PR #39902 - Add policy log field&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a class="link" href="https://github.com/cilium/cilium/issues/42044" target="_blank" rel="noopener"
&gt;GitHub Issue #42044 - Policy log does not work for DROPPED/AUDIT flow&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;</description></item></channel></rss>