<?xml version="1.0" encoding="UTF-8"?><rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Angry dev thoughts</title>
	<atom:link href="https://angry-dev-thoughts.com/feed/" rel="self" type="application/rss+xml" />
	<link>https://angry-dev-thoughts.com/</link>
	<description>Software developers are sometimes angry</description>
	<lastBuildDate>Sun, 02 Feb 2025 13:25:07 +0000</lastBuildDate>
	<language>en-US</language>
	<sy:updatePeriod>
	hourly	</sy:updatePeriod>
	<sy:updateFrequency>
	1	</sy:updateFrequency>
	<generator>https://wordpress.org/?v=6.9.1</generator>

<image>
	<url>https://angry-dev-thoughts.com/wp-content/uploads/2024/09/cropped-android-chrome-512x512-3-32x32.png</url>
	<title>Angry dev thoughts</title>
	<link>https://angry-dev-thoughts.com/</link>
	<width>32</width>
	<height>32</height>
</image> 
	<item>
		<title>How to do performant count of child entities in rich entity with doctrine?</title>
		<link>https://angry-dev-thoughts.com/2025/02/02/how-to-do-performant-count-of-child-entities-in-rich-entity-with-doctrine/</link>
					<comments>https://angry-dev-thoughts.com/2025/02/02/how-to-do-performant-count-of-child-entities-in-rich-entity-with-doctrine/#respond</comments>
		
		<dc:creator><![CDATA[angryDev]]></dc:creator>
		<pubDate>Sun, 02 Feb 2025 13:25:06 +0000</pubDate>
				<category><![CDATA[Doctrine ORM]]></category>
		<category><![CDATA[Domain Driven Design]]></category>
		<category><![CDATA[Programming]]></category>
		<category><![CDATA[Software development]]></category>
		<category><![CDATA[Test Driven Development]]></category>
		<category><![CDATA[Testing]]></category>
		<guid isPermaLink="false">https://angry-dev-thoughts.com/?p=80</guid>

					<description><![CDATA[<p>TLDR: Use Extra Lazy feature from Doctrine ORM: https://www.doctrine-project.org/projects/doctrine-orm/en/3.3/tutorials/extra-lazy-associations.html &#8212; Let&#8217;s imagine that we&#8217;re working on e-commerce platform. Each user can sold maximum 100 items How to do it properly? How to introduce domain limit on doctrine relationships? How can I introduce it? Let&#8217;s use rich entities (trying to follow Domain-Driven-Design and Test-Driven-Development rules): &#60;?php [&#8230;]</p>
<p>The post <a href="https://angry-dev-thoughts.com/2025/02/02/how-to-do-performant-count-of-child-entities-in-rich-entity-with-doctrine/">How to do performant count of child entities in rich entity with doctrine?</a> appeared first on <a href="https://angry-dev-thoughts.com">Angry dev thoughts</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p>TLDR: Use Extra Lazy feature from Doctrine ORM: https://www.doctrine-project.org/projects/doctrine-orm/en/3.3/tutorials/extra-lazy-associations.html</p>



<p>&#8212;</p>



<p>Let&#8217;s imagine that we&#8217;re working on e-commerce platform. Each user can sold maximum 100 items How to do it properly? How to introduce domain limit on doctrine relationships? How can I introduce it? Let&#8217;s use rich entities (trying to follow Domain-Driven-Design and Test-Driven-Development rules):</p>



<pre class="wp-block-preformatted">&lt;?php

use Doctrine\Common\Collections\ArrayCollection;
use Doctrine\Common\Collections\Collection;
use Doctrine\ORM\Mapping as ORM;

#[ORM\Entity]
#[ORM\Table(name: 'users')]
class User
{
    #[ORM\Id]
    #[ORM\GeneratedValue]
    #[ORM\Column(type: 'integer')]
    private int|null $id = null;

    #[ORM\Column(type: 'string', length: 255)]
    private string $name;

    /** @var Collection&lt;int, Item&gt; */
    #[ORM\OneToOne(inversedBy: 'createdBy', targetEntity: Item::class)]
    private Collection $items;

    public function __construct(string $name)
    {
        $this-&gt;name = $name;
        $this-&gt;items = new ArrayCollection();
    }

    public function addItem(Item $item): void
    {
        $this-&gt;items[] = $item;
    }

    public function getItems(): Collection
    {
        return $this-&gt;items;
    }
}</pre>



<p>and item:</p>



<pre class="wp-block-code"><code>&lt;?php

use Doctrine\ORM\Mapping as ORM;

class Item
{
    #&#91;ORM\Id]
    #&#91;ORM\GeneratedValue]
    #&#91;ORM\Column(type: 'integer')]
    private int|null $id = null;

    #&#91;ORM\Column(type: 'string')]
    private string $description;

    #&#91;ORM\Column(type: 'integer')]
    private int $price;

    #&#91;ORM\ManyToOne(targetEntity: User::class, inversedBy: 'items')]
    private User $createdBy;

    public function __construct(string $description, int $price)
    {

    }

    public function setCreator(User $createdBy): void
    {
        $createdBy-&gt;addItem($this);
        $this-&gt;createdBy = $createdBy;
    }
}</code></pre>



<p>And basic test for that:</p>



<pre class="wp-block-code"><code>&lt;?php

namespace tests;

use Item;
use PHPUnit\Framework\TestCase;
use User;

final class ItemsLimitPerUserTest extends TestCase
{
    public function testItemsLimitPerUser(): void
    {
        $user = new User('John');
        $itemA = new Item('My aswesome item A', 20);
        $itemB = new Item('My aswesome item B', 20);
        $itemC = new Item('My aswesome item C', 20);

        $itemA-&gt;setCreator($user);
        $itemB-&gt;setCreator($user);
        $itemC-&gt;setCreator($user);

        $this-&gt;assertEquals(
            3,
            $user-&gt;getItems()-&gt;count()
        );
    }
}</code></pre>



<p>Now let&#8217;s add new test case that adding fourth item will fail (let&#8217;s set limit = 3). Basically we will implement items limit per user logic.</p>



<pre class="wp-block-preformatted">public function testItemsLimitPerUserIsMet(): void<br>{<br>    $user = new User('John');<br>    $itemA = new Item('My aswesome item A', 20);<br>    $itemB = new Item('My aswesome item B', 20);<br>    $itemC = new Item('My aswesome item C', 20);<br>    $itemD = new Item('My aswesome item D', 20);<br><br>    $itemA-&gt;setCreator($user);<br>    $itemB-&gt;setCreator($user);<br>    $itemC-&gt;setCreator($user);<br><br>    try {<br>        $itemD-&gt;setCreator($user);<br>    } catch (Exception $exception) {<br>        $this-&gt;assertInstanceOf(LimitMetException::class, $exception);<br>    }<br><br>    $this-&gt;assertEquals(<br>        3,<br>        $user-&gt;getItems()-&gt;count()<br>    );<br>}</pre>



<p>Which obviously will fail for that moment:</p>



<pre class="wp-block-code"><code>~/Development/doctrine-playground$ ./vendor/bin/phpunit tests
PHPUnit 11.5.6 by Sebastian Bergmann and contributors.

Runtime:       PHP 8.2.27

.F                                                                  2 / 2 (100%)

Time: 00:00.007, Memory: 8.00 MB

There was 1 failure:

1) tests\ItemsLimitPerUserTest::testItemsLimitPerUserIsMet
Failed asserting that 4 matches expected 3.

/home/adt/Development/doctrine-playground/tests/ItemsLimitPerUserTest.php:48

FAILURES!
Tests: 2, Assertions: 2, Failures: 1.
</code></pre>



<p>Now let&#8217;s try to implement this requirement (git diff): </p>



<pre class="wp-block-code"><code>diff --git a/src/User.php b/src/User.php
index ec83b61..d8dcde8 100644
--- a/src/User.php
+++ b/src/User.php
@@ -8,6 +8,8 @@ use Doctrine\ORM\Mapping as ORM;
 #&#91;ORM\Table(name: 'users')]
 class User
 {
+    public const ITEMS_LIMIT = 3;
+
     #&#91;ORM\Id]
     #&#91;ORM\GeneratedValue]
     #&#91;ORM\Column(type: 'integer')]
@@ -26,8 +28,15 @@ class User
         $this-&gt;items = new ArrayCollection();
     }
 
+    /**
+     * @throws LimitMetException
+     */
     public function addItem(Item $item): void
     {
+        if ($this-&gt;items-&gt;count() &gt;= self::ITEMS_LIMIT) {
+            throw new LimitMetException();
+        }
+
         $this-&gt;items&#91;] = $item;
     }
</code></pre>



<p>Now, all tests are passing:</p>



<pre class="wp-block-code"><code>~/Development/doctrine-playground$ ./vendor/bin/phpunit tests
PHPUnit 11.5.6 by Sebastian Bergmann and contributors.

Runtime:       PHP 8.2.27

..                                                                  2 / 2 (100%)

Time: 00:00.003, Memory: 8.00 MB

OK (2 tests, 3 assertions)</code></pre>



<p>But we have one issue, during adding new item doctrine by default will load whole items collection. It&#8217;s not good to load it only to do the count. For that we can use Extra lazy feature from Doctrine ORM:</p>



<pre class="wp-block-code"><code>    /** @var Collection&lt;int, Item> */
    #&#91;ORM\OneToOne(inversedBy: 'createdBy', targetEntity: Item::class, fetch: 'EXTRA_LAZY')]
    private Collection $items;</code></pre>



<p>git diff:</p>



<pre class="wp-block-code"><code>diff --git a/src/User.php b/src/User.php
index d8dcde8..194fe67 100644
--- a/src/User.php
+++ b/src/User.php
@@ -19,7 +19,7 @@ class User
     private string $name;
 
     /** @var Collection&lt;int, Item> */
-    #&#91;ORM\OneToOne(inversedBy: 'createdBy', targetEntity: Item::class)]
+    #&#91;ORM\OneToOne(inversedBy: 'createdBy', targetEntity: Item::class, fetch: 'EXTRA_LAZY')]
     private Collection $items;</code></pre>



<p>Now doctrine won&#8217;t load all entities into memory to simply count them, it will do dedicate count SQL query. In that way you can introduce limit for really large entity collections and avoid hitting memory limit and performance issues.</p>
<p>The post <a href="https://angry-dev-thoughts.com/2025/02/02/how-to-do-performant-count-of-child-entities-in-rich-entity-with-doctrine/">How to do performant count of child entities in rich entity with doctrine?</a> appeared first on <a href="https://angry-dev-thoughts.com">Angry dev thoughts</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://angry-dev-thoughts.com/2025/02/02/how-to-do-performant-count-of-child-entities-in-rich-entity-with-doctrine/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>We should be able to write test for every bug reported showcasing bug</title>
		<link>https://angry-dev-thoughts.com/2025/01/08/we-should-be-able-to-write-test-for-every-bug-reported-showcasing-bug/</link>
					<comments>https://angry-dev-thoughts.com/2025/01/08/we-should-be-able-to-write-test-for-every-bug-reported-showcasing-bug/#respond</comments>
		
		<dc:creator><![CDATA[angryDev]]></dc:creator>
		<pubDate>Wed, 08 Jan 2025 12:08:34 +0000</pubDate>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[Software development]]></category>
		<guid isPermaLink="false">https://angry-dev-thoughts.com/?p=75</guid>

					<description><![CDATA[<p>In my opinion if bug was reported by client then it shouldn’t happen again. Writing good test securing this is worth an effort in many cases. Even simpel unit test showcasing error (if it&#8217;s possible), then it&#8217;s worth to commit test case showing error, and now tests should fail. Then write fix and commit that, [&#8230;]</p>
<p>The post <a href="https://angry-dev-thoughts.com/2025/01/08/we-should-be-able-to-write-test-for-every-bug-reported-showcasing-bug/">We should be able to write test for every bug reported showcasing bug</a> appeared first on <a href="https://angry-dev-thoughts.com">Angry dev thoughts</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p>In my opinion if bug was reported by client then it shouldn’t happen again. Writing good test securing this is worth an effort in many cases. Even simpel unit test showcasing error (if it&#8217;s possible), then it&#8217;s worth to commit test case showing error, and now tests should fail. Then write fix and commit that, now tests should be green.</p>
<p>The post <a href="https://angry-dev-thoughts.com/2025/01/08/we-should-be-able-to-write-test-for-every-bug-reported-showcasing-bug/">We should be able to write test for every bug reported showcasing bug</a> appeared first on <a href="https://angry-dev-thoughts.com">Angry dev thoughts</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://angry-dev-thoughts.com/2025/01/08/we-should-be-able-to-write-test-for-every-bug-reported-showcasing-bug/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>Why Fibonacci for Story Points in Agile Software Development</title>
		<link>https://angry-dev-thoughts.com/2024/12/30/why-fibonacci-for-story-points-in-agile-software-development/</link>
					<comments>https://angry-dev-thoughts.com/2024/12/30/why-fibonacci-for-story-points-in-agile-software-development/#respond</comments>
		
		<dc:creator><![CDATA[angryDev]]></dc:creator>
		<pubDate>Mon, 30 Dec 2024 12:08:16 +0000</pubDate>
				<category><![CDATA[Agile]]></category>
		<category><![CDATA[Scrum]]></category>
		<category><![CDATA[Software development]]></category>
		<guid isPermaLink="false">https://angry-dev-thoughts.com/?p=73</guid>

					<description><![CDATA[<p>Agile software development has transformed how teams approach project management by focusing on flexibility, iterative progress, and constant collaboration. A central part of this process involves estimating the effort needed to complete tasks or user stories. One common method for doing this is through story points, which allow teams to estimate relative effort without tying [&#8230;]</p>
<p>The post <a href="https://angry-dev-thoughts.com/2024/12/30/why-fibonacci-for-story-points-in-agile-software-development/">Why Fibonacci for Story Points in Agile Software Development</a> appeared first on <a href="https://angry-dev-thoughts.com">Angry dev thoughts</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p>Agile software development has transformed how teams approach project management by focusing on flexibility, iterative progress, and constant collaboration. A central part of this process involves <strong>estimating the effort</strong> needed to complete tasks or user stories. One common method for doing this is through <strong>story points</strong>, which allow teams to estimate relative effort without tying themselves to precise measurements like hours or days. Among the different ways to assign story points, the <strong>Fibonacci sequence</strong> is widely used. But <strong>why Fibonacci for story points</strong>? In this article, we’ll explore the role of Fibonacci numbers in Agile story point estimation, how they relate to days, and why they are the preferred choice for many teams.</p>



<h2 class="wp-block-heading">What Are Story Points?</h2>



<p>In Agile methodologies, <strong>story points</strong> are used to estimate the effort, complexity, and time involved in completing a user story or task. These estimates are relative rather than absolute, meaning they don’t correspond directly to hours or days. The purpose of story points is to give teams a sense of how much work is involved in a user story compared to other stories.</p>



<p><strong>Agile story points</strong> help determine how much work a team can realistically take on in a sprint or iteration. The scale is subjective, allowing teams to assign points based on complexity rather than exact time estimates. This method fosters collaboration, avoids overcommitment, and helps teams make informed decisions about the work they can handle during a sprint.</p>



<h2 class="wp-block-heading">Why Fibonacci for Story Points?</h2>



<p>The <strong>Fibonacci sequence</strong> is a series of numbers where each number is the sum of the two preceding ones: 0, 1, 1, 2, 3, 5, 8, 13, 21, 34, and so on. Using the Fibonacci sequence for <strong>Agile story points</strong> is a popular choice because it effectively captures the increasing uncertainty and complexity that comes with larger tasks. But <strong>why Fibonacci for story points</strong> specifically? Here are some key reasons:</p>



<h3 class="wp-block-heading">1. <strong>Reflects Exponential Growth in Complexity</strong></h3>



<p>As tasks get larger or more complex, the effort required to complete them doesn’t just grow linearly—it grows exponentially. Fibonacci numbers grow at an increasing rate, which is a natural fit for capturing the increasing uncertainty and effort required for larger tasks. As a result, <strong>Fibonacci story points</strong> allow teams to better differentiate between simple and complex tasks.</p>



<h3 class="wp-block-heading">2. <strong>Prevents Over-Precision</strong></h3>



<p>One of the drawbacks of estimating in hours or days is the temptation to be overly precise. In Agile, we aim to <strong>avoid false precision</strong> by acknowledging that the exact time it takes to complete a task can vary. Fibonacci numbers, being relatively large, help teams focus on estimating in terms of <strong>relative effort</strong> rather than worrying about precise time measurements. This is especially important in Agile environments, where tasks are often more complex and involve a high degree of uncertainty.</p>



<h3 class="wp-block-heading">3. <strong>Simplifies Estimation</strong></h3>



<p>The Fibonacci sequence provides a simple and intuitive scale for estimating tasks. For teams new to <strong>Agile story points Fibonacci</strong> or estimating in general, it’s easier to think in terms of broad categories like 3, 5, 8, or 13 story points rather than trying to estimate down to the hour. The simplicity of Fibonacci numbers helps reduce analysis paralysis and speeds up the estimation process during <strong>Sprint Planning</strong>.</p>



<h3 class="wp-block-heading">4. <strong>Captures Uncertainty</strong></h3>



<p>The increasing gaps between Fibonacci numbers naturally express the uncertainty and complexity associated with larger tasks. As the size of a task grows, so does the uncertainty, and the Fibonacci sequence reflects this in a way that linear scales (like 1, 2, 3, 4, 5) do not. This makes it easier to estimate larger tasks with a higher degree of flexibility.</p>



<h2 class="wp-block-heading">Fibonacci Story Points to Days</h2>



<p>One common question that arises when using <strong>Fibonacci story points</strong> is how to translate these points into days or hours. The Fibonacci scale is deliberately abstract, designed to measure relative complexity rather than specific time durations. As such, <strong>Fibonacci story points to days</strong> is not a direct conversion. For example, a user story assigned 5 points might not correspond to exactly 5 days of work. Instead, it represents a task that is moderately complex compared to a simpler 3-point task.</p>



<p>However, over time, as teams become more experienced with their <strong>velocity</strong> (the amount of work they can complete in a sprint), they may begin to correlate certain point values with time. For example:</p>



<ul class="wp-block-list">
<li>A <strong>1-point story</strong> might take a day or less, depending on the team’s velocity.</li>



<li>A <strong>5-point story</strong> might take 2-3 days.</li>



<li>An <strong>8-point story</strong> could take several days or even the entire sprint.</li>
</ul>



<p>It’s important to remember that <strong>story points</strong> should never be viewed as direct time estimates. The goal is to measure <strong>relative effort</strong> and complexity, not precise hours. However, as teams mature, they can observe patterns that help them predict how many story points they can tackle in a sprint, which indirectly reflects how much time those points represent in real-world terms.</p>



<h2 class="wp-block-heading">How Fibonacci Story Points Work in Agile</h2>



<p>In Agile, particularly in <strong>Scrum</strong>, the team comes together during <strong>Sprint Planning</strong> to estimate user stories using story points. When using the Fibonacci sequence for estimation, the team will discuss the complexity of each user story and agree on a point value based on their understanding of the effort involved. A common technique for this is <strong>Planning Poker</strong>, where team members simultaneously reveal their estimates, and discrepancies are discussed until a consensus is reached.</p>



<p>The typical Fibonacci scale used in Agile story point estimation looks like this:</p>



<ul class="wp-block-list">
<li><strong>1 Point</strong>: Simple, straightforward task with minimal complexity.</li>



<li><strong>2 Points</strong>: Slightly more effort, but still a manageable task.</li>



<li><strong>3 Points</strong>: Moderate complexity, requiring some effort but not overwhelming.</li>



<li><strong>5 Points</strong>: A task with noticeable complexity, but still feasible within a sprint.</li>



<li><strong>8 Points</strong>: Complex tasks, requiring significant effort and time.</li>



<li><strong>13 Points</strong>: Very large tasks, possibly spanning multiple sprints.</li>
</ul>



<p>As the Fibonacci sequence progresses, the gaps between the numbers grow larger, reflecting the increased uncertainty and complexity. This scaling helps teams more easily differentiate between simpler and more complicated tasks without getting bogged down in detailed estimations.</p>



<h2 class="wp-block-heading">Advantages of Using Fibonacci for Story Points</h2>



<h3 class="wp-block-heading">1. <strong>Increased Estimation Accuracy</strong></h3>



<p>The exponential nature of Fibonacci numbers more accurately reflects the increasing complexity of larger tasks. As tasks grow more complicated, estimating their effort becomes more difficult. <strong>Fibonacci story points</strong> provide a practical way to manage this increasing uncertainty.</p>



<h3 class="wp-block-heading">2. <strong>Faster Estimation Process</strong></h3>



<p>Teams can estimate user stories quickly without getting bogged down in specifics. The Fibonacci sequence provides enough differentiation for most tasks without overcomplicating the process. The simplicity of the system accelerates the decision-making during <strong>Sprint Planning</strong>.</p>



<h3 class="wp-block-heading">3. <strong>Improved Collaboration</strong></h3>



<p>Using <strong>Fibonacci story points</strong> encourages team discussions about the scope of each task, helping ensure a shared understanding. If estimates vary significantly between team members, it leads to valuable conversations that clarify ambiguities and improve team alignment.</p>



<h3 class="wp-block-heading">4. <strong>Facilitates Task Breakdown</strong></h3>



<p>When tasks are estimated at higher point values, it often signals to the team that the task is too large and should be broken down further. This keeps the work manageable and allows teams to better gauge the amount of work they can complete in a sprint.</p>



<h2 class="wp-block-heading">Challenges and Considerations</h2>



<p>While <strong>Agile story points Fibonacci</strong> offers many benefits, it does come with some challenges:</p>



<ul class="wp-block-list">
<li><strong>Subjectivity</strong>: Story point estimation can be subjective, and different team members might have varying views on how difficult a task is. Clear communication and team alignment are essential to ensure accurate estimates.</li>



<li><strong>Difficulty in Transitioning</strong>: Teams new to Agile or those unfamiliar with <strong>Fibonacci for story points</strong> may find it difficult to estimate accurately at first. Over time, the team will learn to refine their estimates based on experience.</li>



<li><strong>Scaling</strong>: For very large projects, the Fibonacci scale might need to be adjusted, especially if tasks regularly reach values like 21 or 34 points. Some teams extend the Fibonacci sequence beyond 13 points to accommodate larger estimates.</li>
</ul>



<h2 class="wp-block-heading">Conclusion</h2>



<p><strong>Why Fibonacci for story points</strong>? The Fibonacci sequence provides an intuitive, scalable, and effective way to estimate effort in Agile software development. It captures the increasing complexity and uncertainty that comes with larger tasks, while avoiding the pitfalls of over-precision and encouraging team collaboration. While <strong>Fibonacci story points to days</strong> doesn’t provide a direct conversion, the system helps teams understand the relative complexity of tasks, which ultimately leads to more informed Sprint Planning and better-managed workloads. By incorporating Fibonacci numbers into the Agile process, teams can enhance their estimation accuracy, improve communication, and ensure a smoother, more predictable development process.</p>
<p>The post <a href="https://angry-dev-thoughts.com/2024/12/30/why-fibonacci-for-story-points-in-agile-software-development/">Why Fibonacci for Story Points in Agile Software Development</a> appeared first on <a href="https://angry-dev-thoughts.com">Angry dev thoughts</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://angry-dev-thoughts.com/2024/12/30/why-fibonacci-for-story-points-in-agile-software-development/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>Non technical project manager/product manager of IT projects is scam</title>
		<link>https://angry-dev-thoughts.com/2024/10/29/non-technical-project-manager-product-manager-of-it-projects-is-scam/</link>
					<comments>https://angry-dev-thoughts.com/2024/10/29/non-technical-project-manager-product-manager-of-it-projects-is-scam/#respond</comments>
		
		<dc:creator><![CDATA[angryDev]]></dc:creator>
		<pubDate>Tue, 29 Oct 2024 12:04:00 +0000</pubDate>
				<category><![CDATA[Agile]]></category>
		<category><![CDATA[Software development]]></category>
		<guid isPermaLink="false">https://angry-dev-thoughts.com/?p=61</guid>

					<description><![CDATA[<p>They do not understand what is going on. They make strange decisions. I belive that managing IT projects requires knowing what&#8217;s under the hood to make informative decisions.</p>
<p>The post <a href="https://angry-dev-thoughts.com/2024/10/29/non-technical-project-manager-product-manager-of-it-projects-is-scam/">Non technical project manager/product manager of IT projects is scam</a> appeared first on <a href="https://angry-dev-thoughts.com">Angry dev thoughts</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p>They do not understand what is going on. They make strange decisions. I belive that managing IT projects requires knowing what&#8217;s under the hood to make informative decisions. </p>
<p>The post <a href="https://angry-dev-thoughts.com/2024/10/29/non-technical-project-manager-product-manager-of-it-projects-is-scam/">Non technical project manager/product manager of IT projects is scam</a> appeared first on <a href="https://angry-dev-thoughts.com">Angry dev thoughts</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://angry-dev-thoughts.com/2024/10/29/non-technical-project-manager-product-manager-of-it-projects-is-scam/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>Starting development of new feature by creating new micro service does not make sense in most cases</title>
		<link>https://angry-dev-thoughts.com/2024/10/27/starting-development-of-new-feature-by-creating-new-micro-service-does-not-make-sense-in-most-cases/</link>
					<comments>https://angry-dev-thoughts.com/2024/10/27/starting-development-of-new-feature-by-creating-new-micro-service-does-not-make-sense-in-most-cases/#respond</comments>
		
		<dc:creator><![CDATA[angryDev]]></dc:creator>
		<pubDate>Sun, 27 Oct 2024 14:37:01 +0000</pubDate>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[Software development]]></category>
		<guid isPermaLink="false">https://angry-dev-thoughts.com/?p=69</guid>

					<description><![CDATA[<p>I think it&#8217;s better to develop core/monolith part and then split it to the microservice if the feature would needed it (high usage, a lot of data, high frequency of changes). In general I don&#8217;t think so there should be auto rules, like new service = new microservice.</p>
<p>The post <a href="https://angry-dev-thoughts.com/2024/10/27/starting-development-of-new-feature-by-creating-new-micro-service-does-not-make-sense-in-most-cases/">Starting development of new feature by creating new micro service does not make sense in most cases</a> appeared first on <a href="https://angry-dev-thoughts.com">Angry dev thoughts</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p>I think it&#8217;s better to develop core/monolith part and then split it to the microservice if the feature would needed it (high usage, a lot of data, high frequency of changes).</p>



<p>In general I don&#8217;t think so there should be auto rules, like new service = new microservice.</p>
<p>The post <a href="https://angry-dev-thoughts.com/2024/10/27/starting-development-of-new-feature-by-creating-new-micro-service-does-not-make-sense-in-most-cases/">Starting development of new feature by creating new micro service does not make sense in most cases</a> appeared first on <a href="https://angry-dev-thoughts.com">Angry dev thoughts</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://angry-dev-thoughts.com/2024/10/27/starting-development-of-new-feature-by-creating-new-micro-service-does-not-make-sense-in-most-cases/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>How to make PHP session sticky/auto renew on last activity</title>
		<link>https://angry-dev-thoughts.com/2024/10/20/how-to-make-php-session-sticky-auto-renew-on-last-activity/</link>
					<comments>https://angry-dev-thoughts.com/2024/10/20/how-to-make-php-session-sticky-auto-renew-on-last-activity/#comments</comments>
		
		<dc:creator><![CDATA[angryDev]]></dc:creator>
		<pubDate>Sun, 20 Oct 2024 14:50:09 +0000</pubDate>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[Software development]]></category>
		<guid isPermaLink="false">https://angry-dev-thoughts.com/?p=66</guid>

					<description><![CDATA[<p>Let&#8217;s talk about php session life managment. What if we want to set it to autorenew based on last activity? How can I do it? Set PHP sesion cookie to be session (session.cookie_lifetime = 0) + set garbage collection time which is calculated since last session_start() [by setting session.gc_maxlifetime=3600 to have session valid for one [&#8230;]</p>
<p>The post <a href="https://angry-dev-thoughts.com/2024/10/20/how-to-make-php-session-sticky-auto-renew-on-last-activity/">How to make PHP session sticky/auto renew on last activity</a> appeared first on <a href="https://angry-dev-thoughts.com">Angry dev thoughts</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p>Let&#8217;s talk about php session life managment. What if we want to set it to autorenew based on last activity? How can I do it? Set PHP sesion cookie to be session (<code>session.cookie_lifetime = 0</code>) + set garbage collection time which is calculated since last session_start() [by setting session.gc_maxlifetime=3600 to have session valid for one hour since last activity]. I&#8217;m taking about those two settings</p>



<pre class="wp-block-code"><code> session.cookie_lifetime int</code></pre>



<blockquote class="wp-block-quote is-layout-flow wp-block-quote-is-layout-flow">
<p>session.cookie_lifetime specifies the lifetime of the cookie in seconds which is sent to the browser. The value 0 means &#8220;until the browser is closed.&#8221; Defaults to 0.</p>



<p><a href="https://www.php.net/manual/en/session.configuration.php#ini.session.cookie-lifetime">https://www.php.net/manual/en/session.configuration.php#ini.session.cookie-lifetime</a></p>
</blockquote>



<pre class="wp-block-code"><code> session.gc_maxlifetime int </code></pre>



<blockquote class="wp-block-quote is-layout-flow wp-block-quote-is-layout-flow">
<p>session.gc_maxlifetime specifies the number of seconds after which data will be seen as &#8216;garbage&#8217; and potentially cleaned up. Garbage collection may occur during session start (depending on session.gc_probability and session.gc_divisor). Defaults to 1440 (24 minutes).</p>



<p><a href="https://www.php.net/manual/en/session.configuration.php#ini.session.gc-maxlifetime">https://www.php.net/manual/en/session.configuration.php#ini.session.gc-maxlifetime</a></p>
</blockquote>



<p>Sometimes I see that people set PHP session cookie lifetime however it does not increase security and only annoys people. Like if set expiration to 24h then when you logged on at 10 AM you will be logged out at 10 AM next day, no matter what.</p>
<p>The post <a href="https://angry-dev-thoughts.com/2024/10/20/how-to-make-php-session-sticky-auto-renew-on-last-activity/">How to make PHP session sticky/auto renew on last activity</a> appeared first on <a href="https://angry-dev-thoughts.com">Angry dev thoughts</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://angry-dev-thoughts.com/2024/10/20/how-to-make-php-session-sticky-auto-renew-on-last-activity/feed/</wfw:commentRss>
			<slash:comments>1</slash:comments>
		
		
			</item>
		<item>
		<title>I don&#8217;t believe dependency inversion princpile makes sense in most cases</title>
		<link>https://angry-dev-thoughts.com/2024/10/13/i-dont-believe-dependency-inversion-princpile-makes-sense-in-most-cases/</link>
					<comments>https://angry-dev-thoughts.com/2024/10/13/i-dont-believe-dependency-inversion-princpile-makes-sense-in-most-cases/#respond</comments>
		
		<dc:creator><![CDATA[angryDev]]></dc:creator>
		<pubDate>Sun, 13 Oct 2024 12:01:43 +0000</pubDate>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[Software development]]></category>
		<guid isPermaLink="false">https://angry-dev-thoughts.com/?p=56</guid>

					<description><![CDATA[<p>I often see that following dependency inversion principle (from SOLID) we end up with many interfaces with just one implementation, and what is more it&#8217;s usually whole public API of given class. In my opinion it doesn&#8217;t make sense. However I do believe in original purpose of this rule. Like the example of deploying embedded [&#8230;]</p>
<p>The post <a href="https://angry-dev-thoughts.com/2024/10/13/i-dont-believe-dependency-inversion-princpile-makes-sense-in-most-cases/">I don&#8217;t believe dependency inversion princpile makes sense in most cases</a> appeared first on <a href="https://angry-dev-thoughts.com">Angry dev thoughts</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p>I often see that following dependency inversion principle (from SOLID) we end up with many interfaces with just one implementation, and what is more it&#8217;s usually whole public API of given class. In my opinion it doesn&#8217;t make sense. However I do believe in original purpose of this rule. Like the example of deploying embedded system, when you can recompile and send through wire less data because you applied interface.</p>



<h2 class="wp-block-heading">So, we should avoid interfaces with one implementation, right?</h2>



<p>From my experience interfaces with one implementation should be avoided. I sometimes hear this explanations from people adding interface with one implementation:</p>



<ul class="wp-block-list">
<li><em>when I have inerfaces (even with one implementation) code is decoupled</em> &#8211; seriously? Adding interfaces changes anything? In my opinion no. If there is need for coupling and there is coupling in real life then it probably should be depicted in the code.</li>



<li><em>when I have inerfaces (even with one implementation) testing is easier</em> &#8211; I can agree with that, however when I saw code people stating that in tests I did not see implementation of this interface Like<em> RepositoryInterface </em>and <em>InMemoryRepository implements RepositoryInterface</em>, and what they do is just creating another mock with mocking library</li>



<li><em>when I have inerfaces (even with one implementation) when I will need second implementation it will be easier</em>  &#8211; happend zero times in my over 10 years experience. Usually abstraction that you will make based on one case won&#8217;t fit more cases. That is why I propose to wait with creating abstractions till you will be able to notice the pattern (at least 3 cases)</li>



<li><em>when I have inerfaces (even with one implementation) it isolates parts of the system</em> &#8211; I can sometimes agree, but usually what I see is the interface that contains whole public API of given class and what is more is changed with the same pace as given concrete class (bruh)</li>
</ul>



<h2 class="wp-block-heading">So what&#8217;s wrong with interface with one implementation?</h2>



<p>In my opinion the less code we write the better, so I don&#8217;t like interfaces with one implementation because:</p>



<ul class="wp-block-list">
<li>they make navigation trough code harder,</li>



<li>you have more code,</li>



<li>they hide real dependency even if there is only one implementation</li>
</ul>



<h2 class="wp-block-heading">So when to use interface?</h2>



<p>From my experience creating abstraction is really hard. That is why I advice to wait till more cases, so you can notice and validate pattern. In general I think that creating interfaces with one implementation is  misinterpeetation of DIP from SOLID, here is quote from Uncle Bob:</p>



<blockquote class="wp-block-quote is-layout-flow wp-block-quote-is-layout-flow">
<p>The need to mock every class interaction forces an explosion of polymorphic interfaces. In statically typed languages like Java, that means the creation of lots of extra interface classes whose sole purpose is to allow mocking. This is over-abstraction and the dreaded “design damage”.</p>



<p><a href="https://blog.cleancoder.com/uncle-bob/2014/05/10/WhenToMock.html">https://blog.cleancoder.com/uncle-bob/2014/05/10/WhenToMock.html</a></p>
</blockquote>



<p></p>
<p>The post <a href="https://angry-dev-thoughts.com/2024/10/13/i-dont-believe-dependency-inversion-princpile-makes-sense-in-most-cases/">I don&#8217;t believe dependency inversion princpile makes sense in most cases</a> appeared first on <a href="https://angry-dev-thoughts.com">Angry dev thoughts</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://angry-dev-thoughts.com/2024/10/13/i-dont-believe-dependency-inversion-princpile-makes-sense-in-most-cases/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>Estimating stories using story points with Fibonacci sequence doesn’t make sense.</title>
		<link>https://angry-dev-thoughts.com/2024/10/06/estimating-story-points-with-fibonacci-doesnt-make-sense/</link>
					<comments>https://angry-dev-thoughts.com/2024/10/06/estimating-story-points-with-fibonacci-doesnt-make-sense/#respond</comments>
		
		<dc:creator><![CDATA[angryDev]]></dc:creator>
		<pubDate>Sun, 06 Oct 2024 11:46:28 +0000</pubDate>
				<category><![CDATA[Agile]]></category>
		<category><![CDATA[Programming]]></category>
		<category><![CDATA[Scrum]]></category>
		<category><![CDATA[Software development]]></category>
		<guid isPermaLink="false">https://angry-dev-thoughts.com/?p=46</guid>

					<description><![CDATA[<p>Did you hear about estimating stories in story points with Fibonacci? Yeah, it may sound fancy, but it is a nightmare in implementations that I saw like you use 1, 2, 3, 5, 8,1 3, and 21 values to estimate your tasks. Then what’s more funny scrum master tends to sum up them and calculate [&#8230;]</p>
<p>The post <a href="https://angry-dev-thoughts.com/2024/10/06/estimating-story-points-with-fibonacci-doesnt-make-sense/">Estimating stories using story points with Fibonacci sequence doesn’t make sense.</a> appeared first on <a href="https://angry-dev-thoughts.com">Angry dev thoughts</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p>Did you hear about estimating stories in story points with Fibonacci? Yeah, it may sound fancy, but it is a nightmare in implementations that I saw like you use 1, 2, 3, 5, 8,1 3, and 21 values to estimate your tasks. Then what’s more funny scrum master tends to sum up them and calculate the average per sprint/per quarter! Like you have no relative scale and you’re trying to do an average that requires values to be relative to each other. For example if you have one task estimated as 3 story points and three tasks for 1 story points it&#8217;s usually like task for 3 story points takes much more time than those three smaller ones together.</p>



<p>I think it is sometimes proposed and forced <a href="https://angry-dev-thoughts.com/2024/09/29/non-tech-scrum-master-is-scam/" data-type="post" data-id="41">by non-tech scrum masters</a>, because they think it needs to be that way. It annoys me. It does not have to be like that.</p>



<p>I really prefer to have a linear scale (with step 1), like:</p>



<ul class="wp-block-list">
<li>1 story point &#8211; around 1 day of development</li>



<li>2 story points &#8211; around 2 days of development</li>



<li>3 story points &#8211; around 3 days of development</li>



<li>4 story points &#8211; around 4 days of development</li>
</ul>



<p>etc. In that way you can really see how much work will fit into sprit.</p>



<h2 class="wp-block-heading">Do not estimate bugs</h2>



<p>Sometimes I hear do not estimate bugs &#8211; and I always think WTF? Without estimating bugs you&#8217;re not able to asses how many of them you are able to take into sprint. Something different is to fix bug that wrong image is shown and something different is to track why wrong price is calculated at the end of quarter. So it should be visible, how much do you expect them to differ. In my opinion esimating bugs is just fine</p>



<h2 class="wp-block-heading">Average story points per sprint</h2>



<p>With usage of story points constrained to values from fibonacci sequence you cannot do regular maths on that numbers. Why? Because they are not proportional. So using arithmetic mean will not give you reliable results. Probably you heard many times why this time we planned sprint using artiehmetic mean from pasts sprints and we still did not deliver all stories. Sounds familiar?</p>
<p>The post <a href="https://angry-dev-thoughts.com/2024/10/06/estimating-story-points-with-fibonacci-doesnt-make-sense/">Estimating stories using story points with Fibonacci sequence doesn’t make sense.</a> appeared first on <a href="https://angry-dev-thoughts.com">Angry dev thoughts</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://angry-dev-thoughts.com/2024/10/06/estimating-story-points-with-fibonacci-doesnt-make-sense/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>Non tech scrum master is a scam</title>
		<link>https://angry-dev-thoughts.com/2024/09/29/non-tech-scrum-master-is-scam/</link>
					<comments>https://angry-dev-thoughts.com/2024/09/29/non-tech-scrum-master-is-scam/#comments</comments>
		
		<dc:creator><![CDATA[angryDev]]></dc:creator>
		<pubDate>Sun, 29 Sep 2024 13:01:55 +0000</pubDate>
				<category><![CDATA[Agile]]></category>
		<category><![CDATA[Scrum]]></category>
		<category><![CDATA[Software development]]></category>
		<guid isPermaLink="false">https://angry-dev-thoughts.com/?p=41</guid>

					<description><![CDATA[<p>Frankly speaking, I don&#8217;t believe in non tech scrum masters. They usually don&#8217;t understand what is going on, asks stupid questions, propose solutions that they not understand. In addition, scrum and agile manifest was founded by tech people (like Kent Beck, Martin Fowler, Robert C. Martin, Ken Schwaber) with deep understanding of software development life [&#8230;]</p>
<p>The post <a href="https://angry-dev-thoughts.com/2024/09/29/non-tech-scrum-master-is-scam/">Non tech scrum master is a scam</a> appeared first on <a href="https://angry-dev-thoughts.com">Angry dev thoughts</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p>Frankly speaking, I don&#8217;t believe in non tech scrum masters. They usually don&#8217;t understand what is going on, asks stupid questions, propose solutions that they not understand. In addition, scrum and agile manifest was founded by tech people (like Kent Beck, Martin Fowler, Robert C. Martin, Ken Schwaber) with deep understanding of software development life cycle. And now sometime scrum master is treated as an entry point to IT.</p>



<p>On the other hand when we have scrum master with deep software developement experience then I think this can be really valuable addition to the team. But of course if he/she in fact had a chance to feel problems that Scrum/Agile supposed to solve. </p>



<p>Non tech scrum master tends to ask and propose strange solutions, like:</p>



<ul class="wp-block-list">
<li>Use CRUD (create, read, update, delete) strategy to divide project in smaller tasks when whole tasks is about new read model&#8230;</li>



<li>Avoid large tasks at all costs even without understanding that splitting given part does not make sens, make developing and testing harder</li>
</ul>



<p>In addition non tech scrum master is usually the person that does not deliver any value at all and you can ask yourseflf what does a scrum master do whole day? That is way I much prefer to have scrum master with real experience in IT world and having two responsiblities, for example</p>



<ul class="wp-block-list">
<li>Being a developer + scrum master</li>



<li>Being a software tester + scrum master</li>
</ul>



<p>Not seperate role, when it is first time working in IT.</p>



<p>What is more non-tech scrum masters sometimes event don&#8217;t know scrum guide (14 pages&#8230;), and they trying to convince you something that even scrum guid does not mentions saying that&#8217;s it in scrum guide.</p>



<h2 class="wp-block-heading">It was not a real scrum &#8211; does it sound familiar?</h2>



<p>What is more I often hear that it was not real scrum. For me tools are for given purpose, we cannot do it something for sake of doing something. If it not works let&#8217;s not do it, instead of blindly following some rules. Yes it is worth to know them, but for me winning point is to know when to not use them, instead of using them all the time.</p>



<h2 class="wp-block-heading">So, scrum is a scam?</h2>



<p>I&#8217;m not saying that. But with implementation that scrum is lead by people who never experience problems that scrum is trying to solve then it won&#8217;t work. And it may be scam.</p>
<p>The post <a href="https://angry-dev-thoughts.com/2024/09/29/non-tech-scrum-master-is-scam/">Non tech scrum master is a scam</a> appeared first on <a href="https://angry-dev-thoughts.com">Angry dev thoughts</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://angry-dev-thoughts.com/2024/09/29/non-tech-scrum-master-is-scam/feed/</wfw:commentRss>
			<slash:comments>3</slash:comments>
		
		
			</item>
		<item>
		<title>How to add sitemap to WordPress?</title>
		<link>https://angry-dev-thoughts.com/2024/09/20/how-to-add-sitemap-to-wordpress/</link>
					<comments>https://angry-dev-thoughts.com/2024/09/20/how-to-add-sitemap-to-wordpress/#respond</comments>
		
		<dc:creator><![CDATA[angryDev]]></dc:creator>
		<pubDate>Fri, 20 Sep 2024 13:52:45 +0000</pubDate>
				<category><![CDATA[WordPress]]></category>
		<guid isPermaLink="false">https://angry-dev-thoughts.com/?p=25</guid>

					<description><![CDATA[<p>As usual, when you do something really rare than it is not easy. The same applies to setting up sitemap in WordPress. There are many plugins. It is annoying to test them. Unfortunately I tested few plugins just to find out that since WordPress 5.5 it is built in functionality: https://make.wordpress.org/core/2020/07/22/new-xml-sitemaps-functionality-in-wordpress-5-5/ Finally, I don&#8217;t need [&#8230;]</p>
<p>The post <a href="https://angry-dev-thoughts.com/2024/09/20/how-to-add-sitemap-to-wordpress/">How to add sitemap to WordPress?</a> appeared first on <a href="https://angry-dev-thoughts.com">Angry dev thoughts</a>.</p>
]]></description>
										<content:encoded><![CDATA[
<p>As usual, when you do something really rare than it is not easy. The same applies to setting up sitemap in WordPress. There are many plugins. It is annoying to test them. Unfortunately I tested few plugins just to find out that since WordPress 5.5 it is built in functionality: <a href="https://make.wordpress.org/core/2020/07/22/new-xml-sitemaps-functionality-in-wordpress-5-5/">https://make.wordpress.org/core/2020/07/22/new-xml-sitemaps-functionality-in-wordpress-5-5/</a></p>



<p>Finally, I don&#8217;t need to by annoyed by browsing through different plugins. </p>



<p>So, I don&#8217;t need plugin, which is good. You can find my sitemap here: <a href="https://angry-dev-thoughts.com/wp-sitemap.xml">https://angry-dev-thoughts.com/wp-sitemap.xml</a></p>
<p>The post <a href="https://angry-dev-thoughts.com/2024/09/20/how-to-add-sitemap-to-wordpress/">How to add sitemap to WordPress?</a> appeared first on <a href="https://angry-dev-thoughts.com">Angry dev thoughts</a>.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://angry-dev-thoughts.com/2024/09/20/how-to-add-sitemap-to-wordpress/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
	</channel>
</rss>
