<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: Abou Kone</title>
    <description>The latest articles on DEV Community by Abou Kone (@devakone).</description>
    <link>https://dev.to/devakone</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F174843%2Fafecbcc3-5f9d-4ab9-9148-d700e098296b.jpeg</url>
      <title>DEV Community: Abou Kone</title>
      <link>https://dev.to/devakone</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/devakone"/>
    <language>en</language>
    <item>
      <title>Have AI changed how you build, or just how fast you build?</title>
      <dc:creator>Abou Kone</dc:creator>
      <pubDate>Tue, 17 Feb 2026 15:47:39 +0000</pubDate>
      <link>https://dev.to/devakone/have-ai-changed-how-you-build-or-just-how-fast-you-build-4mdl</link>
      <guid>https://dev.to/devakone/have-ai-changed-how-you-build-or-just-how-fast-you-build-4mdl</guid>
      <description>&lt;div class="ltag__link"&gt;
  &lt;a href="/devakone" class="ltag__link__link"&gt;
    &lt;div class="ltag__link__pic"&gt;
      &lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F174843%2Fafecbcc3-5f9d-4ab9-9148-d700e098296b.jpeg" alt="devakone"&gt;
    &lt;/div&gt;
  &lt;/a&gt;
  &lt;a href="https://dev.to/devakone/i-built-a-personality-test-for-vibe-coding-11cf" class="ltag__link__link"&gt;
    &lt;div class="ltag__link__content"&gt;
      &lt;h2&gt;I Built a Personality Test for Vibe Coding&lt;/h2&gt;
      &lt;h3&gt;Abou Kone ・ Feb 16&lt;/h3&gt;
      &lt;div class="ltag__link__taglist"&gt;
        &lt;span class="ltag__link__tag"&gt;#vibecoding&lt;/span&gt;
        &lt;span class="ltag__link__tag"&gt;#ai&lt;/span&gt;
        &lt;span class="ltag__link__tag"&gt;#claudecode&lt;/span&gt;
        &lt;span class="ltag__link__tag"&gt;#coding&lt;/span&gt;
      &lt;/div&gt;
    &lt;/div&gt;
  &lt;/a&gt;
&lt;/div&gt;


</description>
      <category>vibecoding</category>
      <category>ai</category>
      <category>claudecode</category>
      <category>coding</category>
    </item>
    <item>
      <title>I Built a Personality Test for Vibe Coding</title>
      <dc:creator>Abou Kone</dc:creator>
      <pubDate>Mon, 16 Feb 2026 00:25:21 +0000</pubDate>
      <link>https://dev.to/devakone/i-built-a-personality-test-for-vibe-coding-11cf</link>
      <guid>https://dev.to/devakone/i-built-a-personality-test-for-vibe-coding-11cf</guid>
      <description>&lt;p&gt;Over the past year, I’ve shipped features and entire applications using Cursor, Claude Code, and Codex. Like everyone else who’s made the switch, the speed of shipping blew me away initially (and it still impresses me to this day) but as much as I enjoy the process and the boost in productity, there was this voice in the back of my head that wondered if the speed was something that I always optimized for, back when manually coding, or something that effectively agents allowed me to do now and that I leaned into heavily? After spending years in management before returning to hands-on building, I kept wondering: has agentic coding actually changed how I approach building software?&lt;/p&gt;

&lt;p&gt;Not the tools. Not the speed. Me. I know my type. I was never the TDD-first, spec-everything-out developer. I was the “get to a prototype quick and learn from it” type. And I think a lot of programmers share a similar honesty, we knew about best practices, better architectural patterns, lean code, and all the methodologies that would help us ship better code. But company culture, time pressure, and tech debt played heavily against our best instincts. Delivery is what mattered.&lt;/p&gt;

&lt;p&gt;So I wondered: now that AI agents can bang out complex, optimized code in seconds, now that you can ship a production-ready app in a weekend if you know what you’re doing - does that change coding personalities?&lt;/p&gt;

&lt;p&gt;One weekend I started building to find out and today I am excited to share the Vibe Coding Profiler:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://www.vibe-coding-profiler.com" rel="noopener noreferrer"&gt;https://www.vibe-coding-profiler.com&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;It started as Project BoloKonon (from the Bambara word meaning “inside the hand” — as in craft). I wanted to create a personality test for my (and your) vibe coding style. What I ended up with is a Vibe Coding Profile (VCP) built on 6 axes that came out of my research. The underlying design principle that drove it was:&lt;/p&gt;

&lt;p&gt;What dimensions of “how you build” with coding agents are actually observable from git metadata alone?&lt;/p&gt;

&lt;p&gt;This is because a thorough analysis would involved sharing part of all of the prompts used as part of the building process, which is both impractical and unsafe so I wondered if git history could (pun intended) tell a story about my vibe coding process. The 6 axes (A through F) used in generating the profile are a synthesis of various existing research or writings:&lt;/p&gt;

&lt;p&gt;TDD and Agile academic research: test-first patterns and planning signals, informing Guardrail Strength (B) and Planning Signal (D)&lt;/p&gt;

&lt;p&gt;GitClear 's developer productivity studies informed code churn and commit pattern analysis, informing Iteration Loop Intensity © and Shipping Rhythm (F)&lt;/p&gt;

&lt;p&gt;Addy Osmani’s excellent writings on agentic coding, especially the conductor vs. orchestrator distinction, which directly informed axes like Automation Heaviness (A) and Surface Area ()E&lt;/p&gt;

&lt;p&gt;A persona taxonomy synthesis from multiple industry frameworks&lt;/p&gt;

&lt;p&gt;How it works:&lt;/p&gt;

&lt;p&gt;Connect with GitHub (GitLab and Bitbucket also available)&lt;br&gt;
Connect a repository&lt;br&gt;
VCP runs an analysis on the metadata from a sampling of commits in your git history&lt;br&gt;
You get assigned a persona based on your patterns&lt;br&gt;
You can optionally enable an LLM-powered analysis for a more comprehensive review of your methodology. Each repo you analyze feeds into a Unified VCP: your baseline coding profile across projects. Since your style might shift depending on the project, you get both individual insights and the aggregate view.&lt;/p&gt;

&lt;p&gt;You can also choose to share your VCP publicly, mine is here:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://www.vibe-coding-profiler.com/u/devakone" rel="noopener noreferrer"&gt;https://www.vibe-coding-profiler.com/u/devakone&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Your profile is private by default, and you choose how much to share. I took security and privacy seriously but it goes without saying, use this for side projects, not work repos. The project is open source and you can contribute at&lt;/p&gt;

&lt;p&gt;&lt;a href="https://github.com/devakone/vibe-coding-profiler" rel="noopener noreferrer"&gt;https://github.com/devakone/vibe-coding-profiler&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;I’ll keep refining the signals as the industry evolves and hopefully others have better idea and as my brother Yannick suggested, maybe this could evolve in a diagnostic tool to help early career coders improve their approach to building effectively. There was quite a bit of iteration, but I’m glad to release V0 today and let the power of community and open source help evolve it&lt;/p&gt;

&lt;p&gt;Give it a vibe and your feedback is always welcome!&lt;/p&gt;

</description>
      <category>vibecoding</category>
      <category>ai</category>
      <category>claudecode</category>
      <category>coding</category>
    </item>
    <item>
      <title>How procrastinating helped me ship a new AI assisted writing platform</title>
      <dc:creator>Abou Kone</dc:creator>
      <pubDate>Thu, 22 Jan 2026 00:27:33 +0000</pubDate>
      <link>https://dev.to/devakone/how-procrastinating-helped-me-ship-a-new-ai-assisted-writing-platform-3f4g</link>
      <guid>https://dev.to/devakone/how-procrastinating-helped-me-ship-a-new-ai-assisted-writing-platform-3f4g</guid>
      <description>&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Frqcj5wf16ntfikj7anbr.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Frqcj5wf16ntfikj7anbr.png" alt=" " width="800" height="696"&gt;&lt;/a&gt;&lt;br&gt;
Where do I start? There are many things that went on here so I guess I'll start from the beginning. I loved writing, and I loved it because I love reading. I'd say I love reading more than writing because I still do read. But there was a time of my life where I found great joy in writing, and that coincided with a time of my life that was most creative, which was when I was coding a lot. Coding got my creative juices flowing, and it was fun enough that I kept doing it outside of work, which kept me busy enough, with side projects. Writing was one of the way that also helped me get that creative energy out in productive ways. Don't expect novel writer here, I did my writing on technical articles tied to what I was learning at work and while I enjoyed the creative writing process, I also found the sharing of knowledge meaningful and rewarding because it helped others, based on the comments and feedback I got on my articles.&lt;/p&gt;

&lt;p&gt;5 or 6 years ago though, that stopped all of a sudden. I stopped enjoying writing, and it became something I dreaded. The thought of sitting down for a time period to focus on writing became something I dreaded. It's as I am writing these words that I now realized that it may have been tied to my career transition in engineering management as opposed to the individual contribution track I had been on. I did and do enjoy engineering leadership, but I now realize that a side effect of it might have been that the lack of active coding may have played a part in shutting off my creativity, or at least not kickstarting it the same that coding does. I have been meaning to get back to writing for a while now, but the thought of sitting down and banging out thoughts on keyboard just made me go ugh, and until recently I always pushed it to the back of my mind.&lt;/p&gt;

&lt;p&gt;"Not in 2026 ", I told myself late last year as I was reflecting on what I wanted to achieve in the upcoming year, "you're going to get yourself back in the game Abou, one article a week, and no excuses". I had been mentally preparing myself for it in different ways; I did and do have a lot of ideas about writing topics that come to me randomly, and I have gotten more disciplined about writing them down in Google Keep when I am out and about. The idea being that I would get back to them and flesh them out in that famous moment of everybody's life where procrastination never happens and things get done: you know exactly, when I am talking about, &lt;strong&gt;later&lt;/strong&gt;. Later never happened so "Not in 2026 again!" I told myself, the first weekend of the year, as I sat down to bang out that first article on my experiences coding with AI over the past year.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;(I am psychoanalyzing myself as I am writing these words and it's crazy that I can now tie the fact that I have been doing a lot of (AI) coding over the past year that I have increasingly felt the need to write again)&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Back to the topic though, I sat down then to write, I thought I was ready and hyped myself into it when Crastinator, the professional devil in charge of procrastination (Pro-Crastinator) whispered these sweet words in my ear: "Are you really gonna write for 1 hour, be interrupted again by the kids, or some other distraction, and then step away and never come back to this again? And feel ashamed about it because you know you need to get this done. You promised it to yourself. You've been doing a lot of AI assisted coding Abou, there is an easier way to do this, you know it, and it involves AI, you can code that now, write later". Truth be told, the words did make sense.&lt;/p&gt;

&lt;p&gt;Crastinator always win when you don't want to do something in the first place and he's a pro at it. Developers know this too well, we can sometimes spend too much time attempting to automate something that would have been faster to do manually. Well in this particular variation of this pattern of procrastinated avoidance (don't look it up, I made it up), instead of writing, I coded &lt;strong&gt;Sabati&lt;/strong&gt;.\&lt;/p&gt;

&lt;p&gt;What is &lt;strong&gt;Sabati&lt;/strong&gt;? There will be a more detailed article on it but let's get it out of the way in the simplest way possible:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;Sabati is a AI based task management system that keeps you on track on long running task by nagging... I am sorry, I mean by nudging you.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;In this first iteration, it applies the nudging to writing&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;I hope that makes sense to you but if it does not maybe explaining how I hope it solves my own problem with writing will make it clearer. First, this article you're reading? I wrote it with Sabati. Full meta monent I know! I started with the idea, which is a version of the current title of the article. I wrote a few sentences, and got prompted with questions, suggestions, and critiques over the past week. It was a trip when I got the first email nudge, at the gym in the morning in between sets. It asked me to consider focusing on either the how I beat procrastination, or the product origin story of Sabati aspect of this story. Sabati kept sending me nudges by email and SMS over the past week, helping me refine the story every time I had time to sit down and write.&lt;/p&gt;

&lt;p&gt;It really got me thinking on how to best put this article together and if you're curious, I thought about it some more, wrote a bit more, and realized that I could not really separate them but it would make sense to just focus on the how I beat procrastination for this story. How am I sure I beat it? Well for me, procrastinating about having to write for one or two hours turned into several feverish nights and weekends over a week to deliver an intelligent task management tool masquerading as a writing platorm. Today I am very pleased to share Sabati with you all, completely free, as a BYOK (Bring Your Own API Key) AI muse to help you push forward with your writing, but even beyond, help you refine your ideas over time. Take a minute and try it for yourself, don't forget to BYOK (OpenAI, Anthropic, Google).&lt;/p&gt;

&lt;p&gt;&lt;a href="https://www.sabati.app" rel="noopener noreferrer"&gt;https://www.sabati.app&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;I am eating my own dog food, so if you're curious to hear more about Sabati as a product, I am cooking up that next story right now. I don't know about you, but I can feel the writing procrastination spirit leaving my body right now.&lt;/p&gt;

&lt;p&gt;Take that, Crastinator!&lt;/p&gt;

</description>
      <category>ai</category>
      <category>productivity</category>
      <category>showdev</category>
      <category>writing</category>
    </item>
    <item>
      <title>How to mock an imported Typescript class with Jest</title>
      <dc:creator>Abou Kone</dc:creator>
      <pubDate>Thu, 02 Apr 2020 23:52:31 +0000</pubDate>
      <link>https://dev.to/codedivoire/how-to-mock-an-imported-typescript-class-with-jest-2g7j</link>
      <guid>https://dev.to/codedivoire/how-to-mock-an-imported-typescript-class-with-jest-2g7j</guid>
      <description>&lt;p&gt;Sooner or later in your unit tests you will run into an issue where you need to import a class into your test and mock it, to keep up with good test hygiene. Jest offers a pretty good &lt;a href="https://jestjs.io/docs/en/es6-class-mocks#spying-on-the-constructor" rel="noopener noreferrer"&gt;how to in their documentation&lt;/a&gt; on how to set it up for ES6 classes but if you try those instructions out of the box with Typescript, you will run into the type monster. This is a quick post to get it working for Typescript if you're using Jest. If you're an Angular developer and have not set up Jest yet, &lt;a href="https://www.amadousall.com/how-to-set-up-angular-unit-testing-with-jest/" rel="noopener noreferrer"&gt;follow this great tutorial&lt;/a&gt; by Amadou Sall, the bonus is that you will also set up &lt;code&gt;jest-preset-angular&lt;/code&gt;, which will help down the road.&lt;/p&gt;

&lt;h3&gt;
  
  
  SoundPlayer Class
&lt;/h3&gt;

&lt;p&gt;Let's say this is your &lt;code&gt;sound-player.ts&lt;/code&gt; file:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;
export class SoundPlayer {
  constructor() {
    this.foo = 'bar';
  }

  playSoundFile(fileName) {
    console.log('Playing sound file ' + fileName);
  }
}
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Notice that this is not a default export. That's an important factor that if you follow the Jest documentation, their examples assumes that you're using default exports, which will matter later on in the mock.&lt;/p&gt;

&lt;h3&gt;
  
  
  SoundPlayer Mock
&lt;/h3&gt;

&lt;p&gt;Now let's say you're writing a unit test for another class, let's say &lt;code&gt;SoundPlayerConsumer&lt;/code&gt; and you want to mock SoundPlayer. If you don't have &lt;a href="https://github.com/kulshekhar/ts-jest" rel="noopener noreferrer"&gt;ts-jest&lt;/a&gt; installed, I highly recommend to add it to your Jest configuration now.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;yarn add --dev ts-jest @types/jest
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Like I mentioned earlier, if you're using &lt;a href="https://github.com/thymikee/jest-preset-angular" rel="noopener noreferrer"&gt;jest-preset-angular&lt;/a&gt;, it already comes "bundled" with ts-jest.&lt;/p&gt;

&lt;p&gt;With ts-jest in the bag, mocking a Typescript class with Jest is as easy as:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;import { mocked } from 'ts-jest/utils';
import { SoundPlayer } from './sound-player';

jest.mock('./sound-player', () =&amp;gt; {
  return {
    SoundPlayer: jest.fn().mockImplementation(() =&amp;gt; {
      return {
        playSoundFile: () =&amp;gt; {},
      };
    })
  };
});

describe('SoundPlayerConsumer', () =&amp;gt; {
  const MockedSoundPlayer = mocked(SoundPlayer, true);

  beforeEach(() =&amp;gt; {
   // Clears the record of calls to the mock constructor function and its methods
   MockedSoundPlayer.mockClear();

  });

  it('We can check if the consumer called the class constructor', () =&amp;gt; {
    const soundPlayerConsumer = new SoundPlayerConsumer();
    expect(MockedSoundPlayer).toHaveBeenCalledTimes(1);
  });

}

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;It's pretty self explanatory but here are some clarification points:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Contrarily to the Jest documentation, since we're not using a default export, we have to reflect the namespace of the exported class module:
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;return {
    SoundPlayer: jest.fn().mockImplementation(() =&amp;gt; {
      return {
        playSoundFile: () =&amp;gt; {},
      };
    }
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If this was a default module, we could have written it simply as:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;  return jest.fn().mockImplementation(() =&amp;gt; {
    return {playSoundFile: mockPlaySoundFile};
  });
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If you're getting a “TypeError: ”X“.default is not a constructor.” when trying to run your tests, it's because you have not reflected the exported namespace properly.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt; The magic here happens because of the &lt;a href="https://github.com/kulshekhar/ts-jest/blob/master/docs/user/test-helpers.md" rel="noopener noreferrer"&gt;mocked&lt;/a&gt; method, which according to the documentation :&lt;/li&gt;
&lt;/ul&gt;

&lt;blockquote&gt;
&lt;p&gt;The mocked test helper provides typings on your mocked modules and even their deep methods, based on the typing of its source. It make use of the latest TypeScript features so you even have argument types completion in the IDE (as opposed to jest.MockInstance).&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;The first tell tale sign that your setup is not right would be getting an error of type &lt;code&gt;error TS2339: Property 'mockClear' does not exist on type X&lt;/code&gt; X being the class you are trying to mock.&lt;/p&gt;

&lt;p&gt;I hope this helps you write better unit tests.&lt;/p&gt;

</description>
      <category>jest</category>
      <category>testing</category>
      <category>angular</category>
      <category>typescript</category>
    </item>
    <item>
      <title>Angular Testability: Dealing with Selenium or Protractor timeouts</title>
      <dc:creator>Abou Kone</dc:creator>
      <pubDate>Wed, 01 Apr 2020 21:40:24 +0000</pubDate>
      <link>https://dev.to/codedivoire/angular-testability-dealing-with-selenium-or-protractor-timeouts-479f</link>
      <guid>https://dev.to/codedivoire/angular-testability-dealing-with-selenium-or-protractor-timeouts-479f</guid>
      <description>&lt;p&gt;Running automated integration tests is a crucial element for any serious CI/CD pipeline and within our company, our QA uses Selenium for that purpose. Angular offers Protractor for that purpose, but to each artisan his tool, our Angular apps are just part of a suite that include non Angular apps and it's easier for the team to test them all using Selenium. &lt;/p&gt;

&lt;p&gt;Anybody that has messed with Protractor knows that one of the early frustrations you will run into is knowing from the Selenium's perspective when the Angular page is done doing what it does and is ready to be tested. For novices that would mean any API calls you would be making to the backend to get data, any animation running on the page that as a user you typically wait for before knowing that yes, this page looks like it's ready for me to interact with. Early on our team ran into just that issue and time and resources being an issue, decided to use timers to wait for a reasonable time for the test to assume that the page is ready to interact with. That works most of the time but of course it's not the way you want to run a long term stable QA solution.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Testability API
&lt;/h2&gt;

&lt;p&gt;For the purpose of testability, Angular exposes the &lt;a href="https://angular.io/api/core/Testability" rel="noopener noreferrer"&gt;Testability API&lt;/a&gt;:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;The Testability service provides testing hooks that can be accessed from the browser and by services such as Protractor. Each bootstrapped Angular application on the page will have an instance of Testability. &lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;Plugging into that API is the way for your testing framework to know when your Angular app is ready to be tested. It uses &lt;a href="https://angular.io/api/core/NgZone" rel="noopener noreferrer"&gt;NgZone&lt;/a&gt; to keep track of all outstanding operations currently running in your application and once they are all completed, marks your application as stable. The way that is done with most selenium scripts is to run a Javascript script from within Selenium that does one of the following:&lt;/p&gt;

&lt;p&gt;Synchronously you can execute a Wait condition that waits for your script to return true like:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Java code
...

 wait.until(new ExpectedCondition&amp;lt;Boolean&amp;gt;() {
            public Boolean apply(WebDriver driver) {
                String angularScriptPath = "src/angular-script.js";
                String angularScript = null;
                try {
                    angularScript = SeleniumWebDriverTest.readFile(angularScriptPath);
                } catch (IOException e) {
                    e.printStackTrace();
                }
                Boolean angularPageLoaded = ((JavascriptExecutor) driver).executeScript(angularScript);

                return angularPageLoaded;
            }
        });

...


&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;and your &lt;code&gt;angular-script.js&lt;/code&gt; would look like&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;return window.getAllAngularTestabilities().findIndex(x=&amp;gt;!x.isStable()) === -1

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Check out this well written article that &lt;a href="https://www.swtestacademy.com/selenium-wait-javascript-angular-ajax/" rel="noopener noreferrer"&gt;explains how to wait for Angular page readiness using Selenium and gives a JSWaiter Java class&lt;/a&gt; that implements the correct approach for Angular &amp;gt; v5. &lt;/p&gt;

&lt;p&gt;You can also go the async way and run an async script in Selenium that will provide a &lt;code&gt;seleniumCallback&lt;/code&gt; callback function that your script will invoke when Angular is ready&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;let rootElement = window.getAllAngularRootElements()[0];
let testability = window.getAngularTestability(rootElement);
testability.whenStable(seleniumCallback);
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;The catch is that this is only half the story, because any async process that you have running in your Angular app needs to indeed be done before Angular thinks that all testabilities are done and ready&lt;/strong&gt;. &lt;/p&gt;

&lt;p&gt;If you have tried this above and it is still not working, it's more than likely because you have an async process running that prevents your app from ever attaining stability for test purposes. This is a particular true if you're using &lt;code&gt;setTimeout&lt;/code&gt; or &lt;code&gt;setInterval&lt;/code&gt;, let's say for example that as soon as the user logs in you launch a &lt;code&gt;setInterval&lt;/code&gt; to determine when their authentication or session tokens expires. If you trigger that a &lt;code&gt;setInterval&lt;/code&gt; as soon as your app boots up, you're toast in terms of testing if you don't take the proper measures as your app testability will never reach the stable point. That will more than likely mean a timeout if you're using Protractor or Selenium.&lt;/p&gt;

&lt;h2&gt;
  
  
  How to get stable
&lt;/h2&gt;

&lt;p&gt;To attain stability for testing if you're using &lt;code&gt;setTimeout&lt;/code&gt; or &lt;code&gt;setInterval&lt;/code&gt; there are two things you can do:&lt;/p&gt;

&lt;h3&gt;
  
  
  Use ngZone.runOutsideAngular()
&lt;/h3&gt;

&lt;p&gt;Use &lt;code&gt;ngZone.runOutsideAngular&lt;/code&gt; if you're doing any work that does not require UI updates. If your work does require UI updates (where change detection is required), you can easily re-enter the Angular Zone by using &lt;code&gt;ngZone.run&lt;/code&gt;. &lt;a href="https://christianliebel.com/2016/11/angular-2-protractor-timeout-heres-fix/" rel="noopener noreferrer"&gt;Check out this article for an in -depth explanation of ngZone and how it works with testability&lt;/a&gt;.&lt;/p&gt;

&lt;h3&gt;
  
  
  Delay starting any timers until you really need to
&lt;/h3&gt;

&lt;p&gt;In my own case I was starting a timer as soon as the user logged in. I just delayed setting that timer until the Angular app is indeed ready for testing. This was a simple as delaying starting the timer in my authentication logic until Angular told testing was ready using a Testability on the Angular zone:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;new Testability(ngZone).whenStable(()=&amp;gt;　{ 
        console.log("Now I am stable");
    　});
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Check out this Stackblitz for an idea on how to do that:&lt;/p&gt;

&lt;p&gt;&lt;iframe src="https://stackblitz.com/edit/angular-o2kkac?" width="100%" height="500"&gt;
&lt;/iframe&gt;
&lt;/p&gt;

&lt;p&gt;With this simple change in the flow, the app reaches testing stability before the other processes can kick in. &lt;/p&gt;

&lt;p&gt;One last thing that might help in debugging this issue for you, how would you know that you have incomplete async tasks still running? Lucky for you, this blitz will help you setup your app to log all running microtasks in your Angular zone. This will allow you to check on any process you might have overlooked that is keeping your app from stabilizing initially:&lt;/p&gt;

&lt;p&gt;&lt;iframe src="https://stackblitz.com/edit/zonejs-pending-tasks?" width="100%" height="500"&gt;
&lt;/iframe&gt;
&lt;/p&gt;

&lt;p&gt;Also check out this &lt;a href="https://stackoverflow.com/questions/48627074/how-to-track-which-async-tasks-protractor-is-waiting-on" rel="noopener noreferrer"&gt;Stackoverflow discussion&lt;/a&gt; for some more context on this issue and how to solve it.&lt;/p&gt;

</description>
      <category>angular</category>
      <category>protractor</category>
      <category>testing</category>
      <category>selenium</category>
    </item>
    <item>
      <title>A day in the life: how a frontend developer solves a "simple" bug</title>
      <dc:creator>Abou Kone</dc:creator>
      <pubDate>Sun, 23 Feb 2020 20:26:24 +0000</pubDate>
      <link>https://dev.to/codedivoire/a-day-in-the-life-how-a-frontend-developer-solves-a-simple-bug-3e98</link>
      <guid>https://dev.to/codedivoire/a-day-in-the-life-how-a-frontend-developer-solves-a-simple-bug-3e98</guid>
      <description>&lt;p&gt;I have been working lately with junior front end developers, as well as mentoring aspiring developers and one of the questions that they ask me is how to become a better/senior developer. That's a question that is hard for me to answer quantitatively but the one quality that I know about senior developers is their ability to solve problems, in a timely fashion. In this post I wanted to illustrate that aspect, but also to give an anecdotal insight into what a day might look like in the life of a front end developer, and the twists and turns that it can take to solve a seemingly simple problem.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Bug
&lt;/h2&gt;

&lt;p&gt;I had implemented a new report page for one of our applications, where the user can create a spreadsheet like report by setting a few parameters. I say spreadsheet like because although it visually looks like a spreadsheet to the user, I implemented it as a flexbox based grid of individual grids, due to other requirements that made it difficult to achieve with a regular table. So far so good, except that to maintain the table appearance, I really need &lt;em&gt;pixel perfect&lt;/em&gt; coherence between the individual grids which after a little tweaking with padding and margins I achieved on Chrome on my Macbook. The code is deployed, everything looks good except for my colleagues running on Windows, they observed a slight shift one some of the columns, breaking the table illusion. To give you an idea, this is what they were observing:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fi%2Fumuzbww9dov81jow10qe.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fi%2Fumuzbww9dov81jow10qe.png" alt="The bug" width="712" height="526"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Easy enough I told myself 8:30ish AM that morning, it's just another rendering issue, I just need to reproduce it and fix it.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Lesson 1: "It works on my machine" should never be a valid developer's answer to a bug. Unless you believe that other people at delusional, you should use it as a basis to start your investigation knowing that at least it works somewhere. It should never be from your perspective the end of it.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fi%2Fgzlvmh1izqx0tkuugyr2.jpg" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fi%2Fgzlvmh1izqx0tkuugyr2.jpg" alt="It Works On My Machine" width="422" height="585"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Reproducing the issue on Chrome/Mac
&lt;/h2&gt;

&lt;p&gt;Like i said, my colleagues on Windows 10 were definitely seeing that bug so I first tried changing the resolution on my Chrome browser to see if it might be related to a responsiveness issue, no dice that way. Next I changed my focus to the operating system and thought that maybe the issue was related to a difference in the Chrome rendering depending on the OS.&lt;/p&gt;

&lt;h2&gt;
  
  
  Reproducing the issue on Chrome/Windows 10 with BrowserStack
&lt;/h2&gt;

&lt;p&gt;Next then was trying it in Chrome on a Windows 10 instance of BrowserStack. After many tries, again no dice. Let's try something else. I remembered I had a IE11/Windows 10 VM lying around for my (non Chrome) Edge. By this time, with standup included, it's 12:00ish PM.&lt;/p&gt;

&lt;h2&gt;
  
  
  Reproducing the issue on Chrome/Windows 10 with VirtualBox
&lt;/h2&gt;

&lt;p&gt;I fired up the VM and tried to reproduce the issue, still no luck. I further probe with my colleagues and it became clear that the issue was resolution related. Their laptop was running on a 1920x1280 resolution and they were easily able to reproduce. i spent the next hour or so trying to get VirtualBox to render my Windows 10 VM guest using that same resolution to no avail. Somewhere in my Googling somebody mentioned using Parallels, which I had already installed. &lt;/p&gt;

&lt;h2&gt;
  
  
  Reproducing the issue on Chrome/Windows 10 with Parallels
&lt;/h2&gt;

&lt;p&gt;With Parallels fired up, I was quickly able to fire up a Windows 10 VM with the correct resolution, install Chrome, which led me to one of my favorite snark for my Windows colleagues&lt;/p&gt;

&lt;p&gt;&lt;iframe class="tweet-embed" id="tweet-1230929236082425859-774" src="https://platform.twitter.com/embed/Tweet.html?id=1230929236082425859"&gt;
&lt;/iframe&gt;

  // Detect dark theme
  var iframe = document.getElementById('tweet-1230929236082425859-774');
  if (document.body.className.includes('dark-theme')) {
    iframe.src = "https://platform.twitter.com/embed/Tweet.html?id=1230929236082425859&amp;amp;theme=dark"
  }



&lt;/p&gt;

&lt;p&gt;and lo and behold on accessing our dev server, the bug was there as soon as the page loaded. After a quick debugging session, I found the culprit behind the rendering issue.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Lesson 2: Be good at accepting when it's time to fold. If you're going down one road and it's not working, learn to quickly re-assess and try something different that will get you closer to your goal.&lt;/strong&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  The Problem
&lt;/h2&gt;

&lt;p&gt;While defining one of the borders for a particular grid, I had used the following code:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;border-top: dashed
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;On Chrome Mac, this translated actually to:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;border-top: dashed 3px;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Basically creating a 3px dashed border by default. I naively assumed that this was the default border with in Chrome. I found that in Windows, leaving Chrome to make the decision actually rendered as:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;border-top: dashed 1px;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;So there was always a 2px difference between the grids. Easy enough, now that I knew the problem, I wanted to switch back to my local env to fix and test the issue. It's around 3:00PM.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Lesson 3: With CSS, be as specific as possible when creating your rules and don't assume.&lt;/strong&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  The Fix
&lt;/h2&gt;

&lt;p&gt;Here again, while trying to work on the fix, I ran into another snag. Our Angular app runs on port 4200, and our API on 8080, which means that even after setting Parallels to be able to access my Mac localhost from my Windows VM, I was still unable to launch the app because of CORS issues. There are many different ways of solving this issue, i quickly tried:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Editing my &lt;code&gt;/etc/hosts&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;ngrok&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;but I decided to make use of the built-in Angular proxy configuration which we had previously used but discarded after enabling CORS on the API. What I thought would be a 1 minute affair turned into an hour when i realize the proxy configuration was not working!&lt;/p&gt;

&lt;h2&gt;
  
  
  The Angular Proxy
&lt;/h2&gt;

&lt;p&gt;I was defining the different api proxy paths in &lt;code&gt;proxy.conf.json&lt;/code&gt; as:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt; "/api": {
    "target": "http://localhost:8080/api",
    "secure": false,
    "logLevel": "debug",
    "changeOrigin": true
  },
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;When the application was running, trying to hit for example &lt;code&gt;/api/reports&lt;/code&gt; would proxy to &lt;code&gt;http://localhost:8080/api&lt;/code&gt; instead of &lt;code&gt;http://localhost:8080/api/reports&lt;/code&gt;. WTF? After re-reading the documentation many times, it finally jumped at me what I was doing wrong and the Angular/Webpack-dev-server people will correctly point out that ,y &lt;code&gt;target&lt;/code&gt; was wrong, I should not add the context path in the &lt;code&gt;target&lt;/code&gt; url but just the host. After changing the configuration to:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt; "/api": {
    "target": "http://localhost:8080",
    "secure": false,
    "logLevel": "debug",
    "changeOrigin": true
  },
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;everything was peachy again and I was able to work and fix the issue properly. Psych! In the meantime, one of the Junior developers submitted a PR for which I had to do a code review, which lead to a video call to go over the code implication in depth since unbeknownst to the dev, his code as implemented would introduce a couple of regression bugs in the code. With that out of the way I was finally able to get back to the issue to fix and deploy, it's around 5:00PM now.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Lesson 4: Pay attention to details, especially syntax and spelling. That's why practices like pair programming and code reviews are important. Having a second set of eyes going over your code will help catch these little errors that we make that take too long for us to catch because we are used to our own code.&lt;/strong&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Summary
&lt;/h2&gt;

&lt;p&gt;What looked like a simple visual CSS bug created a journey that involved of course Google, VirtualBox and Parallels Desktop VMs, Browserstack, Angular and some high level networking (&lt;code&gt;etc/hosts&lt;/code&gt;). I've learned a few things during that process and here are some of the advice from that experience in that day that I would share with aspiring front end developers:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Whoever told you that as a front end developer, you would only be dealing with HTML, CSS and Javascript lied. As you have seen, producing applications require a lot more knowledge that usually, you can't teach directly. It's something that you pick up with experience.&lt;/li&gt;
&lt;li&gt;As a developer, your number one skill to develop is your problem solving. As illustrated here, solving code issues is sometimes not a straightforward affair. You will have to solve problems within problems.&lt;/li&gt;
&lt;li&gt;Take ownership of your work. You are ultimately responsible for the code you produce and it is your duty to ensure that it is of the highest quality.&lt;/li&gt;
&lt;li&gt;Embrace the process. This is what makes our industry so fun but so frustrating at the same time. Things will not always run right, even if (you think) you're doing everything right. Things will break or malfunction, even with your best efforts and part of your job is to figure out how to get them working again.&lt;/li&gt;
&lt;li&gt;For non-coders on the team, it's important to understand that things that look "simple" can turn out not to be so simple, either in implementation or in correcting when it comes to estimations.&lt;/li&gt;
&lt;li&gt;For my non English speaking friends, up your English skills. Like i said, navigating those issues required a lot of Googling and I can't imagine how much slower I would have gone had I not been proficient in English. There is a lot of good information out there and the absolute majority of it is in English, so having a good grasp of the language definitely helps.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;With hindsight now, I went back to BrowserStack and it looks like you can launch a VM with a particular resolution, which would have saved me a couple of hours maybe if I had paid attention. At the end of the day, I found the whole experience funny but not atypical, and I learned some things from it. This is why wanted to share it with others, especially, more junior developers dealing with impostor syndrome to show you that being senior does not mean being all knowing and perfect, it just means that you're gonna "mess up in style" and usually be able to recover from those mess-ups quicker. What about you, do you have any interesting bug or experience that you could share?&lt;/p&gt;

</description>
      <category>frontend</category>
      <category>angular</category>
      <category>productivity</category>
      <category>css</category>
    </item>
    <item>
      <title>How to internationalize a Yup validation schema in a React, Formik and react-i18next app</title>
      <dc:creator>Abou Kone</dc:creator>
      <pubDate>Thu, 13 Jun 2019 13:56:09 +0000</pubDate>
      <link>https://dev.to/codedivoire/how-to-internationalize-a-yup-validation-schema-in-a-react-formik-and-react-i18next-app-cj7</link>
      <guid>https://dev.to/codedivoire/how-to-internationalize-a-yup-validation-schema-in-a-react-formik-and-react-i18next-app-cj7</guid>
      <description>&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fksi1uututik83s9o9zae.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fksi1uututik83s9o9zae.png" width="800" height="449"&gt;&lt;/a&gt;&lt;br&gt;
&lt;span&gt;Internationalization of Yup validation schema with Formik and react-18next&lt;/span&gt;&lt;/p&gt;

&lt;p&gt;Anybody that had to deal with internationalization (shortened as i18n) knows that it can be a real pain if not handled properly, but in the modern Javascript stack, there exists libraries that remove a lot of that pain and actually make it a breeze. One of these libraries is &lt;a href="https://www.i18next.com/" rel="noopener noreferrer"&gt;i18next&lt;/a&gt;. If you work with React, you can’t do better than its react-i18next port for the way it seamlessly exposes the i18next API using all of the major React constructs (&lt;a href="https://react.i18next.com/latest/usetranslation-hook" rel="noopener noreferrer"&gt;Hooks&lt;/a&gt;, &lt;a href="https://react.i18next.com/latest/withtranslation-hoc" rel="noopener noreferrer"&gt;HOCs&lt;/a&gt;, &lt;a href="https://react.i18next.com/latest/translation-render-prop" rel="noopener noreferrer"&gt;Render Props&lt;/a&gt; and &lt;a href="https://react.i18next.com/latest/trans-component" rel="noopener noreferrer"&gt;Components&lt;/a&gt;). &lt;a href="https://jaredpalmer.com/formik/" rel="noopener noreferrer"&gt;Formik&lt;/a&gt; is form management library that promises to allow you to “build forms in React, without the tears” and I can say that indeed so far, my eyes have remained quite dry. Who says form also says validation, and Formik integrates easily with &lt;a href="https://github.com/jquense/yup" rel="noopener noreferrer"&gt;Yup&lt;/a&gt;, a JavaScript object schema validator and object parser. &lt;a href="https://github.com/jquense/yup/issues/159" rel="noopener noreferrer"&gt;Yup supports localization&lt;/a&gt;, but you have to&lt;br&gt;
provide it with a custom locale object, and I felt that the translation functionality should be single handedly handled by i18next. This article will explore how you can sync the translation of the validation errors in Yup when the user changes the selected page language.&lt;/p&gt;
&lt;h3&gt;
  
  
  The Bug
&lt;/h3&gt;

&lt;p&gt;In the StackBlitz below, we have a basic setup of React, react-i18next, Formik and Yup. We display a form with a required email field defined in a Yup schema. This form can also be translated in French. To observe the bug in question in syncing the translation:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Click in the email field&lt;/li&gt;
&lt;li&gt;Click outside&lt;/li&gt;
&lt;li&gt;You should see a &lt;code&gt;Email is required&lt;/code&gt; error.&lt;/li&gt;
&lt;li&gt;Now click on the &lt;code&gt;Francais&lt;/code&gt;link.&lt;/li&gt;
&lt;li&gt;Everything on the page changes to the French translation except for the
validation error.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;iframe src="https://codesandbox.io/embed/react18next-yup-and-formik-basic-example-lbn26"&gt;
&lt;/iframe&gt;
&lt;/p&gt;

&lt;p&gt;I suspect this happens because validation schema is initiated when the component renders with the language set to English initially, and on changing the language, the validation is not re-ran, causing the message to stay in English.&lt;/p&gt;

&lt;h3&gt;
  
  
  The Fix
&lt;/h3&gt;

&lt;p&gt;Luckily the i18next exposes events, in particular the &lt;code&gt;languageChanged&lt;/code&gt; event that we can listen to and update the validation so the validation message can be translated. I initially implemented in a global useEffect hook (that I will share later in this article) that listened for this event and re-ran the form validation , but &lt;a href="https://github.com/jaredpalmer/formik/issues/1395" rel="noopener noreferrer"&gt;this issue on Github had a more elegant solution&lt;/a&gt;, setting all field&lt;br&gt;
with an error to be touched, which should trigger the field validation. The code in question is here:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;
    i18n.on('languageChanged', () =&amp;gt; {
        Object.keys(errors).forEach(fieldName =&amp;gt; {
            setFieldTouched(fieldName)
        })
    })
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;


&lt;p&gt;Here is a blitz of the working translation:&lt;/p&gt;

&lt;p&gt;&lt;iframe src="https://codesandbox.io/embed/89mhe"&gt;
&lt;/iframe&gt;
&lt;/p&gt;

&lt;p&gt;The &lt;code&gt;errors&lt;/code&gt; object and &lt;code&gt;setFieldTouched&lt;/code&gt; function here are the &lt;code&gt;form.errors&lt;/code&gt; and &lt;code&gt;form.setFieldTouched&lt;/code&gt; properties of the Formik &lt;code&gt;form&lt;/code&gt; object passed in a prop. My requirements were different as I only wanted to show an error if the field had indeed been touched.&lt;/p&gt;
&lt;h3&gt;
  
  
  Use a hook
&lt;/h3&gt;

&lt;p&gt;In my particular case, I was dealing not only with field level validation bugs, but I also had nested forms where the same was happening. I created a global hook that takes in a Formik &lt;code&gt;form&lt;/code&gt; object and sets only the fields that have an error as touched. Here is the code:&lt;/p&gt;


&lt;div class="ltag_gist-liquid-tag"&gt;
  
&lt;/div&gt;



&lt;p&gt;This way if the user had previously interacted with the field and gotten a validation error, the translation will re-render the form only with the existing errors translated. You can adjust depending on your business requirements.&lt;/p&gt;

&lt;h3&gt;
  
  
  WithTranslateFormErrors HOC
&lt;/h3&gt;

&lt;p&gt;I’ve created an HOC that you can add to your Formik form that will set this up for you. The code is pretty simple:&lt;/p&gt;


&lt;div class="ltag_gist-liquid-tag"&gt;
  
&lt;/div&gt;


&lt;p&gt;And you would include it in your Formik form like this:&lt;/p&gt;


&lt;div class="ltag_gist-liquid-tag"&gt;
  
&lt;/div&gt;


&lt;p&gt;You don’t need to use the HOC if you’re rendering your Formik form as a&lt;br&gt;
component. In that case, you can just use the &lt;code&gt;useTranslateFormErrors&lt;/code&gt; hook on its own in your render function.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://www.npmjs.com/package/react-i18next-helpers" rel="noopener noreferrer"&gt;This hook and HOC are available as part of the react-i18next-helpers library I recently released&lt;/a&gt;.&lt;/p&gt;




</description>
      <category>react</category>
      <category>internationalization</category>
      <category>translation</category>
    </item>
    <item>
      <title>Angular: When HttpInterceptor doesn’t work with lazy loaded modules</title>
      <dc:creator>Abou Kone</dc:creator>
      <pubDate>Tue, 04 Jun 2019 16:47:58 +0000</pubDate>
      <link>https://dev.to/devakone/angular-when-httpinterceptor-doesn-t-work-with-lazy-loaded-modules-3ipg</link>
      <guid>https://dev.to/devakone/angular-when-httpinterceptor-doesn-t-work-with-lazy-loaded-modules-3ipg</guid>
      <description>&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F2hexmpc9zosswywe2fva.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F2hexmpc9zosswywe2fva.png"&gt;&lt;/a&gt;&lt;br&gt;
&lt;span&gt;Http Interceptor working with a Lazy Loaded Module&lt;/span&gt;&lt;/p&gt;

&lt;p&gt;If you’re doing Angular the right way, you should be using some kind of httpinterceptor. An &lt;a href="https://angular.io/api/common/http/HttpInterceptor" rel="noopener noreferrer"&gt;HttpInterceptor&lt;/a&gt; provides a standard way to intercept HTTP requests and responses and apply custom transformations as suits your application needs. If you’re not familiar with the different use cases for HttpInterceptor, &lt;a href="https://blog.angularindepth.com/top-10-ways-to-use-interceptors-in-angular-db450f8a62d6" rel="noopener noreferrer"&gt;this article from Angular In Depth&lt;/a&gt; will help you understand how you can apply it to your application, and you should. To summarize, you can use interceptors to, amongst other things:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Replace/ urls on the fly&lt;/li&gt;
&lt;li&gt;Hide/Show a loader when loading things&lt;/li&gt;
&lt;li&gt;Add request headers (CORS)&lt;/li&gt;
&lt;li&gt;Handle errors&lt;/li&gt;
&lt;li&gt;Log http operations&lt;/li&gt;
&lt;li&gt;Create a fake backend&lt;/li&gt;
&lt;li&gt;Authentication&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;As you can see, it’s a pretty nifty way to handle some classic requirements of most modern apps.&lt;/p&gt;

&lt;h3&gt;
  
  
  Setting up an HttpInterceptor
&lt;/h3&gt;

&lt;p&gt;Creating an HttpInterceptor is very &lt;a href="https://itnext.io/angular-tutorial-implement-refresh-token-with-httpinterceptor-bfa27b966f57" rel="noopener noreferrer"&gt;straight forward&lt;/a&gt;. In general, you want to create you interceptor as a singleton, so &lt;a href="https://angular.io/guide/singleton-services" rel="noopener noreferrer"&gt;it can be used across your application and only instantiated once by Angular’s DI&lt;/a&gt;. This involves for your average Angular app:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Adding the provider definition to the &lt;code&gt;providers&lt;/code&gt; configuration of &lt;code&gt;CoreModule&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;Importing &lt;code&gt;HttpClientModule&lt;/code&gt;into the &lt;code&gt;imports&lt;/code&gt; configuration of &lt;code&gt;CoreModule&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;Making sure that no other module imports &lt;code&gt;HttpClientModule&lt;/code&gt; in your application
once &lt;code&gt;CoreModule&lt;/code&gt; is imported in your &lt;code&gt;AppModule&lt;/code&gt;. If you don’t use CoreModule (&lt;a href="https://medium.com/@benmohamehdi/angular-best-practices-coremodule-vs-sharedmodule-25f6721aa2ef" rel="noopener noreferrer"&gt;Best practice warning, you
should&lt;/a&gt;), you can directly import &lt;code&gt;HttpClientModule&lt;/code&gt; and your interceptor provider definition into &lt;code&gt;AppModule.&lt;/code&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;One of the key requirements here is that &lt;code&gt;HttpClientModule&lt;/code&gt; is only imported once in your application. The reason why you would want this module to be only be imported once is that this is the module from which we import the&lt;code&gt;HttpClient&lt;/code&gt;service, which is used throughout the application to make HTTP calls. This service is set to handle interceptors should they exist but all interceptors are set up to wok on that single instance of the HttpClient service. Understanding this plays an important role in the next section.&lt;/p&gt;

&lt;h3&gt;
  
  
  Lazy Loaded Modules and HttpInterceptor
&lt;/h3&gt;

&lt;p&gt;&lt;a href="https://angular.io/guide/lazy-loading-ngmodules" rel="noopener noreferrer"&gt;Lazy loaded modules&lt;/a&gt; is a performance related Angular feature that allows modules to only be loaded when their route is visited. This allows your application to bootstrap a lot faster by initially only downloading just the necessary code to get the user to the first actionable screen of your application. One characteristic of lazy loaded modules is that any service declared in the &lt;code&gt;providers&lt;/code&gt; configuration is only available to that module, in Angular speak: “&lt;a href="https://angular.io/guide/ngmodule-faq#why-is-a-service-provided-in-a-lazy-loaded-module-visible-only-to-that-module" rel="noopener noreferrer"&gt;providers of lazy-loaded modules are module-scoped&lt;/a&gt;&lt;em&gt;”.&lt;/em&gt;&lt;br&gt;
Even more specifically:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;When the router creates a component within the lazy-loaded context, Angular&lt;br&gt;
prefers service instances created from these providers to the service instances of the application root injector.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;h3&gt;
  
  
  It doesn’t work!
&lt;/h3&gt;

&lt;p&gt;In my case, I set up a token interceptor that was supposed to be shared&lt;br&gt;
application wide and adds an authentication token to all API bound requests. Debugging showed my that for some calls, the interceptor was getting used, but any other HTTP request from within any of my feature modules was not going through the interceptor at all. Through some more debugging and research, which included some interesting side clarifications on CORS preflight request specification (Did you know that one of a condition for a request to be preflighted &lt;a href="https://stackoverflow.com/questions/39075370/preflight-request-triggers-based-on-content-type" rel="noopener noreferrer"&gt;is if it sets custom headers in the request&lt;/a&gt; (e.g. the request uses a custom header such as &lt;code&gt;x-auth-token&lt;/code&gt;?), I came to better understand why my interceptor was not getting hit.&lt;/p&gt;

&lt;h3&gt;
  
  
  The Why
&lt;/h3&gt;

&lt;p&gt;It came down to having one of the other NPM packages I use in my lazy loaded modules ALSO importing the &lt;code&gt;HttpClientModule&lt;/code&gt; . Everytime that happens, a new instance of the &lt;code&gt;HttpClient&lt;/code&gt; service is injected in the module that of course has not been configured to use the interceptor configured in the &lt;code&gt;CoreModule&lt;/code&gt; .&lt;br&gt;
I could not find a good workaround for this situation short of redeclaring the interceptor provider configuration on each lazy loaded module as a short term workaround while I figure out which package is importing the &lt;code&gt;HttpClientModule&lt;/code&gt; or if Angular accounted for this use case and allows modules to be loaded only if they have not been previously been.&lt;/p&gt;

&lt;h3&gt;
  
  
  The Fix
&lt;/h3&gt;

&lt;p&gt;As of now, I don’t have a clear way to fix this short of not using the libraries that import &lt;code&gt;HttpClientModule&lt;/code&gt; or adding the module-scoped definition of the interceptor provider to each lazy loaded feature.&lt;/p&gt;

&lt;p&gt;I’d appreciate if you ran into this issue or similar and found a way to solve it&lt;br&gt;
in an elegant way to share it in the comments.&lt;/p&gt;

</description>
      <category>angular</category>
      <category>httpinterceptor</category>
    </item>
  </channel>
</rss>
