<?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>Forem: Wiz</title>
    <description>The latest articles on Forem by Wiz (@thewiz).</description>
    <link>https://forem.com/thewiz</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%2F3636498%2Fca6381be-f8aa-4648-a1ea-5dbde3ae0f53.jpg</url>
      <title>Forem: Wiz</title>
      <link>https://forem.com/thewiz</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://forem.com/feed/thewiz"/>
    <language>en</language>
    <item>
      <title>I Got Tired of JavaScript's Date API So I Fixed It</title>
      <dc:creator>Wiz</dc:creator>
      <pubDate>Tue, 09 Dec 2025 17:39:15 +0000</pubDate>
      <link>https://forem.com/thewiz/i-got-tired-of-javascripts-date-api-so-i-fixed-it-95h</link>
      <guid>https://forem.com/thewiz/i-got-tired-of-javascripts-date-api-so-i-fixed-it-95h</guid>
      <description>&lt;p&gt;Look, I'll be real with you. JavaScript's &lt;code&gt;Date&lt;/code&gt; object is a disaster.&lt;/p&gt;

&lt;p&gt;Every time I needed to format a date, I'd find myself Googling "javascript format date" for the hundredth time. Every time I needed to do date math, I triple-checked the math because I didn't trust how it handled months. Don't even get me started on trying to add days to a date without accidentally mutating the original.&lt;/p&gt;

&lt;p&gt;After years of this nonsense, I finally went for it. I was working on a project that needed a lot of date manipulation, and I realized I was spending more time wrestling with dates and building composable functions than actually building features. So I did what any self-respecting developer would do: I built my own solution.&lt;/p&gt;

&lt;h2&gt;
  
  
  Enter WristWatch
&lt;/h2&gt;

&lt;p&gt;&lt;a href="https://www.npmjs.com/package/@lukelowers/wrist-watch" rel="noopener noreferrer"&gt;WristWatch&lt;/a&gt; is my answer to JavaScript's date problems. It's a tiny library (less than 10KB) with zero dependencies that wraps the native &lt;code&gt;Date&lt;/code&gt; API in a way that actually makes sense (at least to me).&lt;/p&gt;

&lt;p&gt;Here's the thing: I didn't want to build some massive framework like Moment.js. I just wanted something that would let me:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Format dates without checking the docs every time&lt;/li&gt;
&lt;li&gt;Do date math without crying&lt;/li&gt;
&lt;li&gt;Remember function names without a PhD in JavaScript archaeology&lt;/li&gt;
&lt;li&gt;Not accidentally mutate dates and break everything&lt;/li&gt;
&lt;/ol&gt;

&lt;h2&gt;
  
  
  The Fun Parts
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Months That Make Sense
&lt;/h3&gt;

&lt;p&gt;This was the first thing I fixed. Native &lt;code&gt;Date.getMonth()&lt;/code&gt; returns 0-11. This is because it's based on Java's old date API and I'm actually cool with that. However, I still needed to account for the zero-based months in my code. In WristWatch, months are 1-12 like a normal human would expect:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;date&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;WristWatch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;2025-12-05&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="nx"&gt;date&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;getMonth&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt; &lt;span class="c1"&gt;// 12 (December, not 11!)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Formatting That Doesn't Suck
&lt;/h3&gt;

&lt;p&gt;Want to format a date? Just tell it what you want:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;now&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;WristWatch&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;now&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
&lt;span class="nx"&gt;now&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;format&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;YYYY-MM-DD&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt; &lt;span class="c1"&gt;// "2025-12-06"&lt;/span&gt;
&lt;span class="nx"&gt;now&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;format&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;MMMM D, YYYY&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt; &lt;span class="c1"&gt;// "December 6, 2025"&lt;/span&gt;
&lt;span class="nx"&gt;now&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;toRelative&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt; &lt;span class="c1"&gt;// "just now"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;No more chaining together a dozen methods or importing an entire formatting library.&lt;/p&gt;

&lt;h3&gt;
  
  
  Date Math That Actually Works
&lt;/h3&gt;

&lt;p&gt;Adding days to a date should be easy. In WristWatch, it is:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;today&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;WristWatch&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;now&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;tomorrow&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;today&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;add&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;day&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;nextWeek&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;today&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;add&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;week&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;nextMonth&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;today&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;add&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;month&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Everything's immutable, so you can't accidentally mess up your original date. And it handles all the annoying edge cases like "what happens when I add a month to January 31st?" (Answer: you get February 28th, not March 3rd.)&lt;/p&gt;

&lt;h3&gt;
  
  
  Comparisons That Don't Make You Think
&lt;/h3&gt;

&lt;p&gt;Need to check if one date is before another? Just do it:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="k"&gt;if &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;tomorrow&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;isAfter&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;today&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;Tomorrow is in the future!&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="k"&gt;if &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;date&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;isBetween&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;start&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;end&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;Date is in range!&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;No timestamp subtraction, no mental math, just straightforward comparisons.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Technical Bits
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Zero Dependencies
&lt;/h3&gt;

&lt;p&gt;I hate bloat. WristWatch has exactly zero dependencies. It's just a thin wrapper around the native &lt;code&gt;Date&lt;/code&gt; API, which means it's fast, reliable, and won't break when some random dependency decides to deprecate itself. F*ck yeah.&lt;/p&gt;

&lt;h3&gt;
  
  
  Fully Typed
&lt;/h3&gt;

&lt;p&gt;Written in TypeScript from the ground up. Every function, every parameter, everything is typed. F*ck yeah.&lt;/p&gt;

&lt;h3&gt;
  
  
  Tree-Shakeable
&lt;/h3&gt;

&lt;p&gt;Only import what you need. Want just the formatting functions? Import just those. F*ck yeah.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="c1"&gt;// Method chaining style&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;WristWatch&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@lukelowers/wrist-watch&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;ww&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;WristWatch&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;now&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
&lt;span class="nx"&gt;ww&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;add&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;day&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;).&lt;/span&gt;&lt;span class="nf"&gt;format&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;YYYY-MM-DD&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

&lt;span class="c1"&gt;// Functional style&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;now&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;format&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;add&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@lukelowers/wrist-watch&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;date&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;now&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
&lt;span class="nf"&gt;format&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nf"&gt;add&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;date&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;getDate&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;day&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;YYYY-MM-DD&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Closely Related to the OG Solution
&lt;/h3&gt;

&lt;p&gt;I didn't want to recreate the original, I wanted to iterate on it. Wrist-Watch is a wrapper so it still reminds you of the old ways. I also didn't want to try to compete with popular methods. I just made what I need. F*ck yeah.&lt;/p&gt;

&lt;h3&gt;
  
  
  Actually Tested
&lt;/h3&gt;

&lt;p&gt;I used property-based testing with fast-check to make sure everything works. Hundreds of random test cases running through every function. The code is also open, so test anything I missed. F*CK YEAH.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Real Talk
&lt;/h2&gt;

&lt;p&gt;Here's the thing about building a date library: everyone tells you not to do it. "Just use Moment!" they say. "Just use date-fns!" they say.&lt;/p&gt;

&lt;p&gt;But Moment is deprecated. date-fns is great but it's huge. And honestly? Sometimes you just want something simple that does exactly what you need without importing half of npm.&lt;/p&gt;

&lt;p&gt;WristWatch isn't trying to be everything to everyone. It's trying to be the library I wish existed. Small, focused, and actually pleasant to use.&lt;/p&gt;

&lt;h2&gt;
  
  
  Want to Try It?
&lt;/h2&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npm &lt;span class="nb"&gt;install&lt;/span&gt; @lukelowers/wrist-watch
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The &lt;a href="https://github.com/lukelowers/wrist-watch" rel="noopener noreferrer"&gt;GitHub repo&lt;/a&gt; has full docs and examples. PRs welcome if you find something broken or want to add a feature.&lt;/p&gt;




&lt;p&gt;Did I over-complicate this? IDK, probably. Did I enjoy building it? Definitely. Will I use it in every project from now on? F*ck yeah.&lt;/p&gt;

&lt;p&gt;Sometimes you just need to scratch your own itch. This was mine.&lt;/p&gt;

</description>
      <category>javascript</category>
      <category>typescript</category>
      <category>npm</category>
      <category>opensource</category>
    </item>
  </channel>
</rss>
