npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2024 – Pkg Stats / Ryan Hefner

react-binding-context

v1.0.0

Published

a performant react context

Downloads

4

Readme

react-lightning-context

A super performant lightning fast context library that only re-renders what has changed and nothing else. This library is a drop in replacement of the official React Context and it is only 12kb!!!!

Why ?

When building web apps at scale one of the main problems is performance over time. When you have 20+ multiple teams contributing to a same code base it is impossible to not hit this bottleneck. This library tries to mitigate some of this problem by providing a Context API that is reliant ant performant. It tries to avoid the un-necessary re-renders problem that the React Context has by only re-rendering what is upmost needed. As a result performance can be boosted dramatically.

This is NOT a state management library. Just a performant React Context replacement. You can also mix this up with redux for example and get a full redux experience but this is outside the scope of this library.

Libraries comparison

The bordered area is where the element is re-rendered. In the examples, the button is updating only one of the properties in the internal Context value.

| Using react-lightning-context | Using React Context | | -------------------------------- | -------------------------------------- | | with gif | without gif |

How to install

  yarn add react-lightning-context

How to use it without Hooks

The main idea is following the same patterns and api that React Context provides with a little twist.

  const defaultValue = { valueA: { a: { b: 222, r: 333 } }, valueB: 222, valueC: 444 };
  const Context = createLightningContext(defaultValue);

  // `listenTo` can be (some examples):
  // - valueA -> { a: { b: 222, r: 333 } }
  // - valueA.a -> { b: 222, r: 333 }
  // - valueA.a.b -> 222

  const ExampleA = () => (
    <Context.Provider>
      <Context.Consumer listenTo={['valueC']}>
        {({ valueC }) => <label>{valueC}</label> }
      </Context.Consumer>
    </Context.Provider>);
};

What is going on here?

  • createLightningContext is creating the context.
  • Context.Provider is defining the area in which the context data is going to be shared.
  • Context.Consumer will listen to changes in the Context value and will re-rendered ONLY when the values on the listenTo prop in the context has changed. You can listen to more than one field, or you can go deep down into the props. ex: valueA.a.r.

How to use it with Hooks

The main idea ia following the same patterns and api that React Context provides with a little twist. This is doing the same as the previous example but with hooks.

  const defaultValue = { valueA: { a: { b: 222, r: 333 } }, valueB: 222, valueC: 444 };
  const Context = createLightningContext(defaultValue);

  const UseLightningContextHookComponent = () => {
    const { valueC } = useLightningContext({ listenTo: ['valueC'] }, Context);
    return <label>{valueC}</label>;
  };

  // `listenTo` can be (some examples):
  // - valueA -> { a: { b: 222, r: 333 } }
  // - valueA.a -> { b: 222, r: 333 }
  // - valueA.a.b -> 222

  const ExampleA = () => (
    <Context.Provider>
      <UseLightningContextHookComponent />
    </Context.Provider>);
};

What is going on here?

  • createLightningContext is creating the context.
  • Context.Provider is defining the area in which the context data is going to be shared.
  • useLightningContext will listen to changes in the Context value and will be updated ONLY when the values on the listenTo prop in the context has changed. You can listen to more than one field, or you can go deep down into the props. ex: valueA.a.r.

API Documentation

| Name | Supported ? | Description | | ------------------------------------------------------------- | ----------- | -------------------------------------------------------------------------------------------- | | React.createContext renamed to createLightningContext | Yes | It is how we create the context we use createLightningContext instead of React.createContext | | Context.Provider | Yes | | | Class.contextType | No | | | Context.displayName | Yes | | | Context.Consumer | Yes | A way of consuming a context value using components. | | useContext renamed to useLightningContext | Yes | A way of consuming a context value using hook. Similar to useContext | | Context.Mutator | New | A component that provides a way of mutating the value of the context | | useLightningContextMutator | New | A Hook that provides a way of mutating the value of the context |

createLightningContext

It follows a similar api that the React.Context provides. It only differs that we have a second parameter with configuration options.

| Parameters | | Types | Required | Values | | ---------------- | -------------------------- | ------- | -------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | | First Parameter | defaultValue | Any | Yes | The default value to initialize the Context | | Second Parameter | Options | Object | No | | | | Options.waitBeforeUpdate | Boolean | | Default: false. This helps when you have a very volatile Context value, that is constantly mutating. This helps by debouncing the updates so you can update the components less times having a similar effect with what concurrentMode will have. |

It returns the Provider, Consumer, Mutator components

Example

const Context = createLightningContext({ value: 'test' });

const Context = createLightningContext({ value: 'test' }, { waitBeforeUpdate: true });

Context.Provider

This does not have any props. Same as React.Context it wraps the context experience.

Example

const Context = createLightningContext({ value: 'test' });

const TopLevelExperience = () => {
  return <Context.Provider>// ... your experience</Context.Provider>;
};

Context.Consumer

This need to be nested inside a Provider component. Same as React.Context it uses the function render pattern and it execution a function when it need to be render.

| Properties | Type | Required | Description | | ---------- | --------------- | -------- | -------------------------------------------------------------------------------- | | listenTo | Array< String > | Yes | Properties from the Context.value that you want to listen to. It can be nested |

It returns a function that is executed passing a mapped object with the binding

Example

const Context = createLightningContext({ value: { first: 1, second: 2 } });

const TopLevelExperience = () => {
  return <Context.Provider>
    <Context.Consumer listenTo={['value.first', 'value.seconds']}>
    {
      (values) => //... anything to render
    }
    </Context.Consumer>
  </Context.Provider>;
};

Return value example

if listenTo is ['value.first', 'value.seconds'] the render function that will execute is

  ({ 'value.first': 123, 'value.seconds': 333 }) => //...anything to render

useLightningContext

Same as Consumer but as a Hook api (similar to the useContext hook)

| Properties | Type | Required | Description | | ---------- | ---------------------------------------- | -------- | -------------------------------------------------------------------------------- | | listenTo | Array | Yes | Properties from the Context.value that you want to listen to. It can be nested | | Context | createLightningContext returned object | Yes | The context you are using |

const result = useLightningContext({ listenTo: [...] }, Context);

Context.Mutator

This need to be nested inside a Provider component. This is a component that provides a callback to update the internal context value. It uses the function render pattern and it execute a function when it need to be render passing the callback. No props are available.

It returns a function that is executed passing a callback function called setContextValue. This will updates the internal values and ONLY re-render what has changed and has someone listening.

Example calling setContextValue

The value parameter is the updated context value

setContextValue((value) => {
  return {
    ...value,
    ...yourChangeGoesHere,
  };
});

Example

const Context = createLightningContext({ value: { first: 1, second: 2 } });

const TopLevelExperience = () => {
  return <Context.Provider>
    <Context.Mutator>
      {
        ({ setContextValue }) => //... anything that want to use setContextValue
      }
    </Context.Mutator>
  </Context.Provider>;
};

useLightningContextMutator

Same as Context.Mutator but as a Hook.

| Properties | Type | Required | Description | | ---------- | ---------------------------------------- | -------- | ------------------------- | | Context | createLightningContext returned object | Yes | The context you are using |

Example

const setContextValue = useLightningContextMutator(Context);