<?xml version="1.0" encoding="utf-8" standalone="yes"?><rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:content="http://purl.org/rss/1.0/modules/content/"><channel><title>Iac on IT Comparison</title><link>https://comparison.metacog.co.kr/tags/iac/</link><description>Recent content in Iac on IT Comparison</description><generator>Hugo</generator><language>en-us</language><lastBuildDate>Sun, 02 Aug 2026 08:55:05 +0900</lastBuildDate><atom:link href="https://comparison.metacog.co.kr/tags/iac/index.xml" rel="self" type="application/rss+xml"/><item><title>Declarative vs Imperative IaC: Describing the End State vs Scripting the Steps</title><link>https://comparison.metacog.co.kr/posts/2026-08-02-declarative-vs-imperative-iac-describing-the-end-state-vs-sc/</link><pubDate>Sun, 02 Aug 2026 08:55:05 +0900</pubDate><guid>https://comparison.metacog.co.kr/posts/2026-08-02-declarative-vs-imperative-iac-describing-the-end-state-vs-sc/</guid><description>&lt;h2 id="overview"&gt;Overview&lt;/h2&gt;
&lt;p&gt;Declarative IaC (e.g. Terraform, CloudFormation) has you specify the desired end state of infrastructure and lets an engine figure out how to get there. Imperative IaC (e.g. shell scripts, Chef recipes, raw CLI calls) has you write the exact sequence of commands to execute. The distinction matters because it determines who — you or the tool — is responsible for ordering, idempotency, and reconciling drift.&lt;/p&gt;
&lt;h2 id="comparison-diagram"&gt;Comparison Diagram&lt;/h2&gt;
&lt;div class="compare-diagram"&gt;
&lt;svg viewBox="0 0 640 360" xmlns="http://www.w3.org/2000/svg"&gt;&lt;text x="160" y="28" text-anchor="middle" font-size="16" style="fill:var(--primary)"&gt;Declarative&lt;/text&gt;&lt;rect x="40" y="50" width="240" height="55" rx="6" style="fill:var(--compare-a-soft);stroke:var(--compare-a)" stroke-width="1.5"/&gt;&lt;text x="160" y="72" text-anchor="middle" font-size="12" style="fill:var(--content)"&gt;Desired State&lt;/text&gt;&lt;text x="160" y="90" text-anchor="middle" font-size="11" style="fill:var(--secondary)"&gt;"3 servers, 1 LB"&lt;/text&gt;&lt;line x1="160" y1="105" x2="160" y2="130" style="stroke:var(--compare-a)" stroke-width="1.5"/&gt;&lt;polygon points="160,140 155,130 165,130" style="fill:var(--compare-a)"/&gt;&lt;rect x="40" y="145" width="240" height="55" rx="6" style="fill:var(--compare-a-soft);stroke:var(--compare-a)" stroke-width="1.5"/&gt;&lt;text x="160" y="167" text-anchor="middle" font-size="12" style="fill:var(--content)"&gt;Engine Computes Diff&lt;/text&gt;&lt;text x="160" y="185" text-anchor="middle" font-size="11" style="fill:var(--secondary)"&gt;plan + dependency graph&lt;/text&gt;&lt;line x1="160" y1="200" x2="160" y2="225" style="stroke:var(--compare-a)" stroke-width="1.5"/&gt;&lt;polygon points="160,235 155,225 165,225" style="fill:var(--compare-a)"/&gt;&lt;rect x="40" y="240" width="240" height="55" rx="6" style="fill:var(--compare-a-soft);stroke:var(--compare-a)" stroke-width="1.5"/&gt;&lt;text x="160" y="262" text-anchor="middle" font-size="12" style="fill:var(--content)"&gt;Infrastructure&lt;/text&gt;&lt;text x="160" y="280" text-anchor="middle" font-size="11" style="fill:var(--secondary)"&gt;converges to match state&lt;/text&gt;&lt;text x="160" y="320" text-anchor="middle" font-size="11" style="fill:var(--secondary)"&gt;Engine decides how &amp;amp; in what order&lt;/text&gt;&lt;line x1="320" y1="20" x2="320" y2="340" style="stroke:var(--border)" stroke-width="1" stroke-dasharray="4,4"/&gt;&lt;text x="480" y="28" text-anchor="middle" font-size="16" style="fill:var(--primary)"&gt;Imperative&lt;/text&gt;&lt;rect x="360" y="45" width="240" height="40" rx="6" style="fill:var(--compare-b-soft);stroke:var(--compare-b)" stroke-width="1.5"/&gt;&lt;text x="480" y="70" text-anchor="middle" font-size="12" style="fill:var(--content)"&gt;Step 1: Create VPC&lt;/text&gt;&lt;line x1="480" y1="85" x2="480" y2="100" style="stroke:var(--compare-b)" stroke-width="1.5"/&gt;&lt;polygon points="480,110 475,100 485,100" style="fill:var(--compare-b)"/&gt;&lt;rect x="360" y="115" width="240" height="40" rx="6" style="fill:var(--compare-b-soft);stroke:var(--compare-b)" stroke-width="1.5"/&gt;&lt;text x="480" y="140" text-anchor="middle" font-size="12" style="fill:var(--content)"&gt;Step 2: Launch Servers&lt;/text&gt;&lt;line x1="480" y1="155" x2="480" y2="170" style="stroke:var(--compare-b)" stroke-width="1.5"/&gt;&lt;polygon points="480,180 475,170 485,170" style="fill:var(--compare-b)"/&gt;&lt;rect x="360" y="185" width="240" height="40" rx="6" style="fill:var(--compare-b-soft);stroke:var(--compare-b)" stroke-width="1.5"/&gt;&lt;text x="480" y="210" text-anchor="middle" font-size="12" style="fill:var(--content)"&gt;Step 3: Attach LB&lt;/text&gt;&lt;line x1="480" y1="225" x2="480" y2="240" style="stroke:var(--compare-b)" stroke-width="1.5"/&gt;&lt;polygon points="480,250 475,240 485,240" style="fill:var(--compare-b)"/&gt;&lt;rect x="360" y="255" width="240" height="40" rx="6" style="fill:var(--compare-b-soft);stroke:var(--compare-b)" stroke-width="1.5"/&gt;&lt;text x="480" y="280" text-anchor="middle" font-size="12" style="fill:var(--content)"&gt;Infrastructure&lt;/text&gt;&lt;text x="480" y="320" text-anchor="middle" font-size="11" style="fill:var(--secondary)"&gt;Author decides exact steps &amp;amp; order&lt;/text&gt;&lt;/svg&gt;
&lt;/div&gt;
&lt;h2 id="comparison-table"&gt;Comparison Table&lt;/h2&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Aspect&lt;/th&gt;
&lt;th&gt;Declarative&lt;/th&gt;
&lt;th&gt;Imperative&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Authoring model&lt;/td&gt;
&lt;td&gt;Write a &lt;strong class="kw"&gt;desired-state spec&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Write an &lt;strong class="kw"&gt;ordered command list&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Execution engine&lt;/td&gt;
&lt;td&gt;Resolves a &lt;strong class="kw"&gt;dependency graph&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Runs a &lt;strong class="kw"&gt;sequential interpreter&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;State tracking&lt;/td&gt;
&lt;td&gt;Maintains a &lt;strong class="kw"&gt;state file&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;&lt;strong class="kw"&gt;Stateless&lt;/strong&gt; execution&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Applying changes&lt;/td&gt;
&lt;td&gt;Single &lt;strong class="kw"&gt;apply&lt;/strong&gt; command&lt;/td&gt;
&lt;td&gt;Run the &lt;strong class="kw"&gt;script/playbook&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Ordering &amp;amp; dependencies&lt;/td&gt;
&lt;td&gt;&lt;strong class="kw"&gt;Auto-resolved&lt;/strong&gt; by engine&lt;/td&gt;
&lt;td&gt;&lt;strong class="kw"&gt;Manually sequenced&lt;/strong&gt; by author&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Idempotency&lt;/td&gt;
&lt;td&gt;&lt;strong class="kw"&gt;Guaranteed&lt;/strong&gt; by design&lt;/td&gt;
&lt;td&gt;&lt;strong class="kw"&gt;Developer-enforced&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Drift detection&lt;/td&gt;
&lt;td&gt;Built-in &lt;strong class="kw"&gt;plan diff&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;&lt;strong class="kw"&gt;Not built-in&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Failure handling&lt;/td&gt;
&lt;td&gt;Partial apply, &lt;strong class="kw"&gt;replan&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;&lt;strong class="kw"&gt;Manual rollback&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;h2 id="key-differences"&gt;Key Differences&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;Declarative code answers &amp;lsquo;what&amp;rsquo;, imperative code answers &lt;strong class="kw"&gt;&amp;lsquo;how&amp;rsquo;&lt;/strong&gt;.&lt;/li&gt;
&lt;li&gt;Declarative tools rely on a &lt;strong class="kw"&gt;state file&lt;/strong&gt; to know current vs. desired infrastructure; imperative scripts have no memory of prior runs.&lt;/li&gt;
&lt;li&gt;Idempotent re-runs are &lt;strong class="kw"&gt;automatic&lt;/strong&gt; in declarative tools but must be hand-coded (checks, conditionals) in imperative scripts.&lt;/li&gt;
&lt;li&gt;Declarative engines build a &lt;strong class="kw"&gt;dependency graph&lt;/strong&gt; to order operations; imperative code hardcodes that order line by line.&lt;/li&gt;
&lt;li&gt;Drift correction in declarative IaC is a matter of re-running &lt;strong class="kw"&gt;plan/apply&lt;/strong&gt;; imperative approaches require re-running or rewriting the exact script.&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id="when-to-use-each"&gt;When to Use Each&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;Declarative&lt;/strong&gt;&lt;/p&gt;</description></item></channel></rss>