Skip to content

Instantly share code, notes, and snippets.

View donaldpipowitch's full-sized avatar

Donald Pipowitch donaldpipowitch

View GitHub Profile
@donaldpipowitch
donaldpipowitch / README.md
Last active June 13, 2022 04:24
React - Error Boundary strategy

One cool feature of React which isn't highlighted that often are "error boundaries".

Error boundaries can catch errors which are thrown inside your component during a lifecycle. You can use them in very fine-granular levels wrapping very small components (but I rarely see this) or you can wrap your whole app and show some fallback content, if an error happens. But you can also wrap something in between those extrem ranges and add a proper reset. Also it's not a hidden secret how to do that I haven't see a lot of people talking about that. So here is a small example which use react-router-dom to do that. You can see the complete example here.

Let's imagine you have the following app:

import * as React from 'react';
import { render } from 'react-dom';
import { Link, BrowserRouter, Switch, Route, Redirect } from 'react-router-dom';
@donaldpipowitch
donaldpipowitch / index.tsx
Created June 27, 2020 19:46
Example how to use 'amazon-cognito-identity-js'
import {
CognitoUserPool,
CognitoUserAttribute,
CognitoUser,
AuthenticationDetails,
CognitoUserSession,
CodeDeliveryDetails,
} from 'amazon-cognito-identity-js';
import React, { FC, useState } from 'react';
@donaldpipowitch
donaldpipowitch / README.md
Created July 1, 2020 13:17
Cheat Sheet for various Brackets

Know your brackets!

  ( ) – parentheses, round brackets, first brackets
  { } – braces, curly brackets, second brackets, moustache brackets 👨🏻
  [ ] – square brackets, third brackets
  ⟨ ⟩ - angle brackets (aka. _not_ less-than/greater-than signs 👀)
  ‹ › - angle quotes (aka. _not_ less-than/greater-than signs 👀)
  < > - less-than/greater-than signs
@donaldpipowitch
donaldpipowitch / index.js
Last active July 7, 2020 07:36
ESLint rule to check for duplicated exported names.
// @ts-check
/** @type {import("eslint").Rule.RuleModule} */
const rule = {
meta: {
docs: {
description: `You can export a type and a value with the same name in the same file, but that confuses refactoring tools.`,
},
},
create(context) {
@donaldpipowitch
donaldpipowitch / index.js
Created July 7, 2020 07:38
ESLint rule to check for round brackets in Jest `test` names. (Doesn't play nicely with --testNamePattern without escaping.)
// @ts-check
/** @type {import("eslint").Rule.RuleModule} */
const rule = {
meta: {
docs: {
description: `If you use a Jest test name like "hello (world)" you can't run \`$ jest -t "hello (world)"\` to select this test.`,
},
fixable: 'code',
},
@donaldpipowitch
donaldpipowitch / mocked-storage.tsx
Last active July 22, 2020 13:10
useSessionStorage and useLocalStorage for easy mocking - similar to MemoryRouter in react-router, but for storage
import React, { FC, useMemo } from 'react';
import {
LocalStorageProvider,
SessionStorageProvider,
} from './use-storage';
// this is just a dumb mock of the storage interface
class MemoryStorage implements Storage {
private data: Record<string, string> = {};
@donaldpipowitch
donaldpipowitch / use-location-state.ts
Created July 22, 2020 06:23
useLocationState: a glorified location.state for React Router as a hook
import { useState, useEffect } from 'react';
import { useLocation, useHistory } from 'react-router-dom';
import { useSessionStorage } from './use-storage'; // see https://gist.github.com/donaldpipowitch/7310d7b9e4b6d467134c425e8732adc6
type UseLocationStateOptions<T> = {
defaultValue?: T;
scope?: string;
filter?: (value: T) => boolean;
};
@donaldpipowitch
donaldpipowitch / use-stable-memo.ts
Last active October 15, 2020 08:12
useStableMemo
import { DependencyList, useState, useEffect, useRef } from 'react';
// use this instead of useMemo of you need a stable value
// see https://twitter.com/0xca0a/status/1314326386555924480
export function useStableMemo<T>(factory: () => T, deps: DependencyList): T {
const [value, setValue] = useState<T>(factory);
const firstRun = useRef(true);
useEffect(
() => {
@donaldpipowitch
donaldpipowitch / get-nice-upper-bound.ts
Created November 13, 2020 07:05
Nice upper bound (e.g. for charts, ticks, scales)
function getNiceUpperBound(value: number) {
const zeroCount = String(Math.round(value)).length - 1;
const factor = Math.pow(10, zeroCount);
return Math.ceil(value / factor) * factor;
}
const upperBound = getNiceUpperBound(3464634); // 4000000
@donaldpipowitch
donaldpipowitch / README.md
Last active January 26, 2023 10:14
Create a codemod with Prettier and Babel

Every now and then I'd like to apply a so called codemod to my a codebase. A codemod is a piece of code which modifies other code. Very often this is done by running some transformation on the abstract syntax tree (AST).

Whenever I need to do this I look for "What is the best way to apply a codemod on my TS code base right now?", because when I only do this every couple of month I either have forgotten about how to do it or tools have changed and my old way stopped working... or both. Surprisingly every time I search for that I found the existing tools bloated or quirky or not matching my workflow.

As I already use Babel to compile our source code I would like to create a Babel plugin which transforms my code. Sadly Babel alone is not good in preserving whitespace and formatting. Thankfully I use Prettier for that and because Prettier uses Babel internally I can create a Babel visitor to transform my source code.

The actually easiest and _most r