Giter VIP home page Giter VIP logo

ad-hok-utils's People

Stargazers

 avatar  avatar  avatar

Watchers

 avatar  avatar

ad-hok-utils's Issues

Should addIsInitialRender() make sure that it's true during effects on mount?

Currently I think isInitialRender would be false in eg an addEffectOnMount() (after the addIsInitialRender in the chain) because it uses its own internal addEffectOnMount() which would run first?

So if isInitialRender should be true during other effects on mount, I think it'd have to eg update its ref during the second render cycle instead?

Add other variants of suppressUnlessProp()?

There are combinations of condition on which to branch (nullishness vs non-nullishness vs truthiness vs falsiness vs empty array vs null vs non-null vs undefined vs non-undefined) + renderNothing() vs returns() something

Might be ideal to optionally accept a returns option to specify a returns() instead of a default renderNothing()? So then just expose eg branchIfNullish() (aka suppressUnlessProp()), branchUnlessNullish(), branchIfTruthy(), branchIfFalsy(), branchIfEmpty(), branchUnlessEmpty(), branchIfNull(), branchUnlessNull(), branchIfUndefined(), branchUnlessUndefined()?

And do the expected type-narrowing (per discussion with @peterstuart, probably can't do type-narrowing for truthy or non-empty array? Although wouldn't truthy be able to at least be narrowed if the prop in question is an actual boolean (via Exclude<TProp, false>)?

Create README

Should include install instructions and docs for each helper

Should ad-hok be a peer dependency?

Seems like to avoid version conflicts between the version of ad-hok used by the project and the internal ad-hok dependency of ad-hok-utils, it should not include its own version of ad-hok and should use a peer dependency instead?

Helper idea: addStateToggler()

"Shorthand" for common addStateHandlers() pattern where it's just a boolean state prop and a "toggler" handler

Implementation from a project:

import {CurriedPropsAdder, addStateHandlers} from 'ad-hok'

type AddStateToggler = <
  TProps,
  TStateName extends string,
  TTogglerName extends string
>(
  stateName: TStateName,
  togglerName: TTogglerName,
  initialValue?: boolean
) => CurriedPropsAdder<
  TProps,
  {
    [stateName in TStateName]: boolean
  } &
    {
      [togglerName in TTogglerName]: () => void
    }
>

const addStateToggler: AddStateToggler = (
  stateName,
  togglerName,
  initialValue = false
) =>
  addStateHandlers(
    {
      [stateName]: initialValue,
    },
    {
      [togglerName]: ({[stateName]: stateValue}) => () => ({
        [stateName]: !stateValue,
      }),
    }
  ) as any

export default addStateToggler

forcePropType() helper?

It seems like eg in a case where the ad-hok prop-adding type "fudging" (of using &) isn't working (eg if you want to reuse an existing prop name in a non-narrowing way), you could follow that with a helper that forces that prop to a specified type?

Not sure if that would have to "infect" the resulting type with Omit?

Seems like the rough alternative would be to expose alternate "honest" typings for the prop-adding ad-hok helpers?

Helper idea: branchIfFailsPredicate()

This appears to be working and is another nice declarative type-narrowing branch() helper:

import { ReactElement } from 'react'
import { branch, returns, renderNothing } from 'ad-hok'

// https://stackoverflow.com/a/62097481/732366
type ExtractPredicateType<TTypePredicate> = TTypePredicate extends (
  value: any
) => value is infer TPredicateType
  ? TPredicateType
  : never

type BranchIfFailsPredicate = <
  TProps extends {},
  TPropName extends keyof TProps,
  TTypePredicate extends (value: TProps[TPropName]) => boolean
>(
  propName: TPropName,
  typePredicate: TTypePredicate,
  opts?: {
    returns?: (props: TProps) => ReactElement<any, any> | null
  }
) => (
  props: TProps
) => TProps &
  {
    [propName in TPropName]: ExtractPredicateType<TTypePredicate>
  }

export const branchIfFailsPredicate: BranchIfFailsPredicate = (
  propName,
  typePredicate,
  opts
) =>
  branch(
    ({ [propName]: propValue }) => !typePredicate(propValue as any),
    opts?.returns ? returns(opts.returns) : renderNothing()
  ) as any

So eg branchIfFailsPredicate('foo', isString) should result in a narrowed type for foo of string after it in the chain

Helper idea: addTriggerRerender()

A useful helper would be to add a declarative triggerRerender() handler prop to the chain

This can be implemented by eg:

addStateHandlers(
  {
    count: 0
  },
  {
    triggerRerender: ({count}) => () => ({
      count: count + 1,
    }),
  }
),
cleanupProps('count')

Then another possibly-worth-including-here abstraction on top of this + addInterval() would be eg addRerenderingEveryNSeconds(5)?

Helper idea: addRemountingWhenPropsChange()

Per usage on Sage and discussion with @peterstuart, a declarative helper for triggering key-based remounting whenever certain props change is very useful

As opposed to the Sage implementation (which relied on serializing the specified props), it's a better idea to do an increment-a-counter-key-when-props-change-effect approach, probably in combination with doing prop identity stabilization on behalf of the caller

So maybe target this signature (I'd be inclined to identity-stabilize by default but allow it to be opted out of if you want to avoid the extra cost of isEqual() comparisons and are effectively taking responsibility for identity stabilization yourself):

addRemountingWhenPropsChange(['foo', 'bar'], {shouldStabilizeIdentity: false})

addReducerOverProps() helper?

If we're only including the "static reducer" form of useReducer() in ad-hok via addReducer(), then makes sense to include a curried-over-props variant here (and explain/link to it from the ad-hok docs)?

Use leading _ for helper-internal props

Per discussion with @peterstuart, this seems like a good convention for saying "if prop namespace collisions happen here, it's fair game" (while in reality making it highly likely (along with helper-specific prop naming) that any collision will actually occur) + "this prop is internal"

Helper idea: add branchIfTruthy()?

I ran into a use case for branchIfTruthy() (the opposite of branchIfFalsy()). Probably wouldn't do any useful type-narrowing (I guess could narrow out true) but would be a useful shorthand

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.