<?xml version="1.0" encoding="utf-8" standalone="yes"?><rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom"><channel><title>Testing on Osmar Petry</title><link>https://osmarpetry.dev/tags/testing/</link><description>Recent content in Testing on Osmar Petry</description><generator>Hugo</generator><language>en-US</language><lastBuildDate>Sat, 12 Jul 2025 00:00:00 +0000</lastBuildDate><atom:link href="https://osmarpetry.dev/tags/testing/rss.xml" rel="self" type="application/rss+xml"/><item><title>XState — model UI behavior correctly and make it testable</title><link>https://osmarpetry.dev/blog/xstate-model-ui-bahavior/</link><pubDate>Sat, 12 Jul 2025 00:00:00 +0000</pubDate><guid>https://osmarpetry.dev/blog/xstate-model-ui-bahavior/</guid><description>&lt;h2 id="the-problem-were-solving"&gt;The problem we&amp;rsquo;re solving&lt;/h2&gt;&#10;&lt;p&gt;Imagine you join a company that runs an e-commerce platform. Product asks you to build a &lt;strong&gt;search page&lt;/strong&gt; — the kind of page every user hits dozens of times a day. It sounds simple: a text input, a button, show results.&lt;/p&gt;&#10;&lt;p&gt;But then reality kicks in. The page has to handle empty queries, network failures, slow connections, retries, and race conditions where a user submits a second search before the first one finishes. A junior developer might reach for a handful of &lt;code&gt;useState&lt;/code&gt; calls — &lt;code&gt;isLoading&lt;/code&gt;, &lt;code&gt;hasError&lt;/code&gt;, &lt;code&gt;data&lt;/code&gt;, &lt;code&gt;submitted&lt;/code&gt; — and suddenly you&amp;rsquo;re juggling four booleans that produce sixteen possible combinations. Most of those combinations are impossible, but nothing in the code prevents them. A loading spinner stays visible after an error. A success message flashes before the data arrives. Bugs creep in not because the developer made a logic error, but because the &lt;strong&gt;model itself was never defined&lt;/strong&gt;.&lt;/p&gt;</description></item><item><title>TDD Effects on Quality and Productivity</title><link>https://osmarpetry.dev/blog/tdd-systematic-review-2016/</link><pubDate>Tue, 15 Apr 2025 00:00:00 +0000</pubDate><guid>https://osmarpetry.dev/blog/tdd-systematic-review-2016/</guid><description>&lt;h2 id="abstract"&gt;Abstract&lt;/h2&gt;&#10;&lt;p&gt;Systematic review of 27 empirical studies (1999–2014) on Test-Driven Development (TDD). Evaluates internal code quality, external product quality, and productivity. Findings: TDD generally improves cohesion and reduces coupling; external quality gains are observed in 88% of cases; productivity results vary, showing improvements in academic settings but a decrease in industrial environments.&lt;/p&gt;&#10;&lt;h2 id="key-points"&gt;Key points&lt;/h2&gt;&#10;&lt;ul&gt;&#10;&lt;li&gt;&lt;strong&gt;Internal quality:&lt;/strong&gt; Improves in 76% of evaluated cases, showing lower coupling, reduced cyclomatic complexity, and higher cohesion (often measured via CK Metrics).&lt;/li&gt;&#10;&lt;li&gt;&lt;strong&gt;External quality:&lt;/strong&gt; Positive impact in 88% of the scenarios, with significant defect reduction in critical systems.&lt;/li&gt;&#10;&lt;li&gt;&lt;strong&gt;Productivity:&lt;/strong&gt; Mixed outcomes. Academic environments reported speed gains, while industrial settings reported a productivity dip.&lt;/li&gt;&#10;&lt;li&gt;&lt;strong&gt;Moderators:&lt;/strong&gt; Prior unit testing experience and continuous integration adoption amplify benefits.&lt;/li&gt;&#10;&lt;li&gt;&lt;strong&gt;Limitations:&lt;/strong&gt; Selection bias, uncontrolled environmental variables, self-reported productivity metrics.&lt;/li&gt;&#10;&lt;/ul&gt;&#10;&lt;h2 id="connections"&gt;Connections&lt;/h2&gt;&#10;&lt;ul&gt;&#10;&lt;li&gt;Aligns with Clean Code principles and CK metrics usage.&lt;/li&gt;&#10;&lt;li&gt;Supports discussions on technical debt in agile processes.&lt;/li&gt;&#10;&lt;li&gt;Contrasts with test-last approaches in rapid prototyping.&lt;/li&gt;&#10;&lt;li&gt;Relates to research on developer psychology and TDD adoption.&lt;/li&gt;&#10;&lt;/ul&gt;&#10;&lt;h2 id="questions"&gt;Questions&lt;/h2&gt;&#10;&lt;ul&gt;&#10;&lt;li&gt;How to tailor TDD for volatile requirements?&lt;/li&gt;&#10;&lt;li&gt;What is the maintenance cost of large test suites over time?&lt;/li&gt;&#10;&lt;li&gt;Are metrics like branch coverage sufficient to gauge TDD effectiveness?&lt;/li&gt;&#10;&lt;li&gt;How does TDD coexist with generative AI in testing workflows?&lt;/li&gt;&#10;&lt;/ul&gt;&#10;&lt;h2 id="personal-reflections"&gt;Personal reflections&lt;/h2&gt;&#10;&lt;ul&gt;&#10;&lt;li&gt;TDD excels for complex business logic; less so for simple CRUD modules.&lt;/li&gt;&#10;&lt;li&gt;CK metrics help quantify internal quality gains.&lt;/li&gt;&#10;&lt;li&gt;Variability explains why some companies abandon TDD after superficial adoption.&lt;/li&gt;&#10;&lt;li&gt;Integrating TDD with BDD could boost external quality.&lt;/li&gt;&#10;&lt;/ul&gt;&#10;&lt;h2 id="detailed-notes"&gt;Detailed notes&lt;/h2&gt;&#10;&lt;ul&gt;&#10;&lt;li&gt;&lt;strong&gt;Methodology:&lt;/strong&gt; PRISMA-based review of 27 empirical studies.&lt;/li&gt;&#10;&lt;li&gt;&lt;strong&gt;Variables:&lt;/strong&gt; Internal quality (CBO, LCOM, WMC, RFC), external quality (defects, MTBF, user satisfaction), productivity (delivery speed, cognitive effort).&lt;/li&gt;&#10;&lt;li&gt;&lt;strong&gt;Results:&lt;/strong&gt; 76% of cases showed increased internal quality (coupling reduction, ~20% cohesion increase, lower cyclomatic complexity); 88% showed increased external quality (defect reduction); proficiency reached after initial productivity dip, mostly observed in academic scenarios.&lt;/li&gt;&#10;&lt;li&gt;&lt;strong&gt;Limitations:&lt;/strong&gt; Many studies lacked controls for prior testing expertise; productivity data often self-reported; publication bias toward positive outcomes.&lt;/li&gt;&#10;&lt;/ul&gt;&#10;&lt;h2 id="example-in-go"&gt;Example in Go&lt;/h2&gt;&#10;&lt;div class="highlight"&gt;&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-go" data-lang="go"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="kn"&gt;package&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;cpf&lt;/span&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="kn"&gt;import&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s"&gt;&amp;#34;testing&amp;#34;&lt;/span&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="kd"&gt;func&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;TestCPFRejectsAllZero&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;t&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="nx"&gt;testing&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;T&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt;&#9;&lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;IsValid&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;&amp;#34;00000000000&amp;#34;&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt;&#9;&#9;&lt;/span&gt;&lt;span class="nx"&gt;t&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;Error&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;&amp;#34;All-zero CPF should be invalid&amp;#34;&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt;&#9;&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="kd"&gt;func&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;TestCPFValidKnownValue&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;t&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="nx"&gt;testing&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;T&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt;&#9;&lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;!&lt;/span&gt;&lt;span class="nf"&gt;IsValid&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;&amp;#34;52998224725&amp;#34;&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt;&#9;&#9;&lt;/span&gt;&lt;span class="nx"&gt;t&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;Error&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;&amp;#34;Valid CPF was rejected&amp;#34;&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt;&#9;&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="kd"&gt;func&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nf"&gt;IsValid&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;cpf&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kt"&gt;string&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kt"&gt;bool&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt;&#9;&lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nb"&gt;len&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;cpf&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;!=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;11&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt;&#9;&#9;&lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;false&lt;/span&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt;&#9;&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt;&#9;&lt;/span&gt;&lt;span class="k"&gt;for&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;:=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;i&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nb"&gt;len&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;cpf&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt;&#9;&#9;&lt;/span&gt;&lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;cpf&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nx"&gt;i&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="o"&gt;!=&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nx"&gt;cpf&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt;&#9;&#9;&#9;&lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="c1"&gt;// Simplified logic for example&lt;/span&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt;&#9;&#9;&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt;&#9;&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="w"&gt;&#9;&lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;false&lt;/span&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;&#10;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h2 id="references"&gt;References&lt;/h2&gt;&#10;&lt;ul&gt;&#10;&lt;li&gt;Bissi, W., Seca Neto, A. G. S., &amp;amp; Emer, M. C. F. P. (2016). The effects of test driven development on internal quality, external quality and productivity: A systematic review. &lt;em&gt;Information and Software Technology&lt;/em&gt;. &lt;a href="https://www.sciencedirect.com/science/article/abs/pii/S0950584916300222" target="_blank" rel="noreferrer"&gt;https://www.sciencedirect.com/science/article/abs/pii/S0950584916300222&lt;/a&gt;&lt;/li&gt;&#10;&lt;li&gt;Additional supporting documents (ResearchGate, CK Metrics literature).&lt;/li&gt;&#10;&lt;/ul&gt;&#10;&lt;h2 id="related-notes"&gt;Related Notes&lt;/h2&gt;&#10;&lt;ul&gt;&#10;&lt;li&gt;&lt;span&#10; class="post-inline-link--missing"&#10; aria-label="Gophers Workshop — Deploy-First Go Architecture. Page does not exist."&#10; title="Page does not exist."&#10; data-tooltip-message="Page does not exist."&#10; &gt;Gophers Workshop — Deploy-First Go Architecture&lt;/span&gt;&lt;/li&gt;&#10;&lt;li&gt;&lt;span&#10; class="post-inline-link--missing"&#10; aria-label="Design &amp;amp;amp; Analysis of Algorithms — Course Overview. Page does not exist."&#10; title="Page does not exist."&#10; data-tooltip-message="Page does not exist."&#10; &gt;Design &amp;amp; Analysis of Algorithms — Course Overview&lt;/span&gt;&lt;/li&gt;&#10;&lt;li&gt;&lt;span&#10; class="post-inline-link--missing"&#10; aria-label="Assembly Study Plan. Page does not exist."&#10; title="Page does not exist."&#10; data-tooltip-message="Page does not exist."&#10; &gt;Assembly Study Plan&lt;/span&gt;&lt;/li&gt;&#10;&lt;li&gt;&lt;a class="post-inline-link" href="https://osmarpetry.dev/blog/bdd/"&gt;BDD&lt;/a&gt;&lt;/li&gt;&#10;&lt;li&gt;&lt;span&#10; class="post-inline-link--missing"&#10; aria-label="Code Smells and Maintainability. Page does not exist."&#10; title="Page does not exist."&#10; data-tooltip-message="Page does not exist."&#10; &gt;Code Smells and Maintainability&lt;/span&gt;&lt;/li&gt;&#10;&lt;li&gt;&lt;span&#10; class="post-inline-link--missing"&#10; aria-label="Enterprise UI Development — Testing, Standards, and Ego Control. Page does not exist."&#10; title="Page does not exist."&#10; data-tooltip-message="Page does not exist."&#10; &gt;Enterprise UI Development — Testing, Standards, and Ego Control&lt;/span&gt;&lt;/li&gt;&#10;&lt;li&gt;&lt;a class="post-inline-link" href="https://osmarpetry.dev/blog/testing-concepts-notes/"&gt;Testing Concepts Notes&lt;/a&gt;&lt;/li&gt;&#10;&lt;/ul&gt;</description></item><item><title>Behavior-Driven Development (BDD)</title><link>https://osmarpetry.dev/blog/bdd/</link><pubDate>Wed, 15 Jan 2025 00:00:00 +0000</pubDate><guid>https://osmarpetry.dev/blog/bdd/</guid><description>&lt;h2 id="what-is-bdd"&gt;What Is BDD&lt;/h2&gt;&#10;&lt;p&gt;BDD bridges the gap between business stakeholders and developers by expressing requirements as executable specifications. Instead of writing tests after the fact, you describe the &lt;strong&gt;expected behavior&lt;/strong&gt; of the system in plain language, then automate those descriptions.&lt;/p&gt;&#10;&lt;p&gt;The core loop: &lt;strong&gt;Discovery&lt;/strong&gt; (what should the system do?) → &lt;strong&gt;Formulation&lt;/strong&gt; (write it in Gherkin) → &lt;strong&gt;Automation&lt;/strong&gt; (implement step definitions).&lt;/p&gt;&#10;&lt;h2 id="bdd-vs-tdd"&gt;BDD vs TDD&lt;/h2&gt;&#10;&lt;p&gt;TDD focuses on unit-level correctness (&amp;ldquo;does this function return the right value?&amp;rdquo;). BDD focuses on system-level behavior (&amp;ldquo;does this feature work from the user&amp;rsquo;s perspective?&amp;rdquo;). In practice they complement each other — use TDD for internal logic, BDD for acceptance and integration tests.&lt;/p&gt;</description></item><item><title>Testing Concepts Notes</title><link>https://osmarpetry.dev/blog/testing-concepts-notes/</link><pubDate>Fri, 15 Jan 2021 00:00:00 +0000</pubDate><guid>https://osmarpetry.dev/blog/testing-concepts-notes/</guid><description>&lt;h2 id="bdd"&gt;&lt;strong&gt;BDD&lt;/strong&gt;&lt;/h2&gt;&#10;&lt;p&gt;BDD (Behavior Driven Development) is a method of testing where you use &amp;ldquo;Given&amp;rdquo; for the scenario, &amp;ldquo;When&amp;rdquo; for the environment of the action, and &amp;ldquo;Then&amp;rdquo; for the action.&lt;/p&gt;&#10;&lt;p&gt;Imagine &lt;strong&gt;AutoLot&lt;/strong&gt;, a car dealership chain building an online vehicle marketplace. A product manager, a developer, and a QA engineer sit together and write this scenario in plain English:&lt;/p&gt;&#10;&lt;div class="highlight"&gt;&lt;pre tabindex="0" class="chroma"&gt;&lt;code class="language-fallback" data-lang="fallback"&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;Given a customer browsing the SUV category&#10;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;When the customer clicks &amp;#34;Schedule Test Drive&amp;#34; on a 2024 Honda CR-V&#10;&lt;/span&gt;&lt;/span&gt;&lt;span class="line"&gt;&lt;span class="cl"&gt;Then the test drive request should appear as &amp;#34;pending&amp;#34; in the customer&amp;#39;s dashboard&#10;&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;This is BDD in practice — the three roles agree on the expected behavior before any code is written. The npm package &lt;code&gt;jest-cucumber&lt;/code&gt; lets you map these Gherkin-style scenarios directly to Jest tests.&lt;/p&gt;</description></item><item><title>Testing Library vs Enzyme</title><link>https://osmarpetry.dev/blog/testing-library-vs-enzyme/</link><pubDate>Fri, 15 Jan 2021 00:00:00 +0000</pubDate><guid>https://osmarpetry.dev/blog/testing-library-vs-enzyme/</guid><description>&lt;h2 id="introduction"&gt;&lt;strong&gt;Introduction&lt;/strong&gt;&lt;/h2&gt;&#10;&lt;p&gt;Testing Library is built around a simple philosophy: the more your tests resemble the way your software is used, the more confidence they can give you. Its three core principles are: tests only break when your app breaks (not when implementation details change), you interact with your app the same way as your users, and built-in selectors find elements the way users do to help you write inclusive code.&lt;/p&gt;</description></item></channel></rss>