Gathering detailed insights and metrics for react-tracked
Gathering detailed insights and metrics for react-tracked
Gathering detailed insights and metrics for react-tracked
Gathering detailed insights and metrics for react-tracked
@objectiv/plugin-react-router-tracked-components
React Router 6 automatically tracked Link and NavLink Components for Objectiv React Tracker
@adhawk/react-tracked-link
A React component for catching and reporting errors
@tracked/health
Health module
zustand-tracked
A small library that allows all your zustand store selectors to be tracked, optimizing computations and rerenders.
State usage tracking with Proxies. Optimize re-renders for useState/useReducer, React Redux, Zustand and others.
npm install react-tracked
Typescript
Module System
Node Version
NPM Version
95.8
Supply Chain
99.5
Quality
77
Maintenance
100
Vulnerability
100
License
TypeScript (89.22%)
JavaScript (10.78%)
Total Downloads
12,966,542
Last Day
26,918
Last Week
173,650
Last Month
796,875
Last Year
6,657,939
MIT License
2,808 Stars
473 Commits
70 Forks
19 Watchers
12 Branches
12 Contributors
Updated on Jul 08, 2025
Latest Version
2.0.1
Package Id
react-tracked@2.0.1
Unpacked Size
36.41 kB
Size
8.96 kB
File Count
24
NPM Version
10.7.0
Node Version
18.20.4
Published on
Sep 10, 2024
Cumulative downloads
Total Downloads
Last Day
17.6%
26,918
Compared to previous day
Last Week
0.6%
173,650
Compared to previous week
Last Month
14.9%
796,875
Compared to previous month
Last Year
81.8%
6,657,939
Compared to previous year
2
31
State usage tracking with Proxies. Optimize re-renders for useState/useReducer, React Redux, Zustand and others.
Documentation site: https://react-tracked.js.org
Preventing re-renders is one of performance issues in React. Smaller apps wouldn't usually suffer from such a performance issue, but once apps have a central global state that would be used in many components. The performance issue would become a problem. For example, Redux is usually used for a single global state, and React-Redux provides a selector interface to solve the performance issue. Selectors are useful to structure state accessor, however, using selectors only for performance wouldn't be the best fit. Selectors for performance require understanding object reference equality which is non-trival for beginners and experts would still have difficulties for complex structures.
React Tracked is a library to provide so-called "state usage tracking." It's a technique to track property access of a state object, and only triggers re-renders if the accessed property is changed. Technically, it uses Proxies underneath, and it works not only for the root level of the object but also for deep nested objects.
Prior to v1.6.0, React Tracked is a library to replace React Context use cases for global state. React hook useContext triggers re-renders whenever a small part of state object is changed, and it would cause performance issues pretty easily. React Tracked provides an API that is very similar to useContext-style global state.
Since v1.6.0, it provides another building-block API which is capable to create a "state usage tracking" hooks from any selector interface hooks. It can be used with React-Redux useSelector, and any other libraries that provide useSelector-like hooks.
This package requires some peer dependencies, which you need to install by yourself.
1npm add react-tracked react scheduler
There are two main APIs createContainer
and createTrackedSelector
.
Both take a hook as an input and return a hook (or a container including a hook).
There could be various use cases. Here are some typical ones.
useValue
custom hook1import { useState } from 'react'; 2 3const useValue = () => 4 useState({ 5 count: 0, 6 text: 'hello', 7 });
This can be useReducer or any hook that returns a tuple [state, dispatch]
.
1import { createContainer } from 'react-tracked'; 2 3const { Provider, useTracked } = createContainer(useValue);
1const Counter = () => { 2 const [state, setState] = useTracked(); 3 const increment = () => { 4 setState((prev) => ({ 5 ...prev, 6 count: prev.count + 1, 7 })); 8 }; 9 return ( 10 <div> 11 <span>Count: {state.count}</span> 12 <button type="button" onClick={increment}> 13 +1 14 </button> 15 </div> 16 ); 17};
The useTracked
hook returns a tuple that useValue
returns,
except that the first is the state wrapped by proxies and
the second part is a wrapped function for a reason.
Thanks to proxies, the property access in render is tracked and
this component will re-render only if state.count
is changed.
1const App = () => ( 2 <Provider> 3 <Counter /> 4 <TextBox /> 5 </Provider> 6);
useTrackedSelector
from useSelector
1import { useSelector, useDispatch } from 'react-redux'; 2import { createTrackedSelector } from 'react-tracked'; 3 4const useTrackedSelector = createTrackedSelector(useSelector);
1const Counter = () => { 2 const state = useTrackedSelector(); 3 const dispatch = useDispatch(); 4 return ( 5 <div> 6 <span>Count: {state.count}</span> 7 <button type="button" onClick={() => dispatch({ type: 'increment' })}> 8 +1 9 </button> 10 </div> 11 ); 12};
1import create from 'zustand'; 2 3const useStore = create(() => ({ count: 0 }));
useTrackedStore
from useStore
1import { createTrackedSelector } from 'react-tracked'; 2 3const useTrackedStore = createTrackedSelector(useStore);
1const Counter = () => { 2 const state = useTrackedStore(); 3 const increment = () => { 4 useStore.setState((prev) => ({ count: prev.count + 1 })); 5 }; 6 return ( 7 <div> 8 <span>Count: {state.count}</span> 9 <button type="button" onClick={increment}> 10 +1 11 </button> 12 </div> 13 ); 14};
This library internally uses use-context-selector
,
a userland solution for useContextSelector
hook.
React 18 changes useReducer behavior which use-context-selector
depends on.
This may cause an unexpected behavior for developers.
If you see more console.log
logs than expected,
you may want to try putting console.log
in useEffect.
If that shows logs as expected, it's an expected behavior.
For more information:
https://github.com/dai-shi/lets-compare-global-state-with-react-hooks
The examples folder contains working examples. You can run one of them with
1PORT=8080 pnpm run examples:01_minimal
and open http://localhost:8080 in your web browser.
You can also try them directly: 01 02 03 04 05 06 07 08 09 10 11 12 13
See this for details.
No vulnerabilities found.
Reason
no dangerous workflow patterns detected
Reason
no binaries found in the repo
Reason
license file detected
Details
Reason
packaging workflow detected
Details
Reason
3 commit(s) and 0 issue activity found in the last 90 days -- score normalized to 2
Reason
Found 3/30 approved changesets -- score normalized to 1
Reason
no effort to earn an OpenSSF best practices badge detected
Reason
detected GitHub workflow tokens with excessive permissions
Details
Reason
dependency not pinned by hash detected -- score normalized to 0
Details
Reason
security policy file not detected
Details
Reason
project is not fuzzed
Details
Reason
SAST tool is not run on all commits -- score normalized to 0
Details
Reason
30 existing vulnerabilities detected
Details
Score
Last Scanned on 2025-07-14
The Open Source Security Foundation is a cross-industry collaboration to improve the security of open source software (OSS). The Scorecard provides security health metrics for open source projects.
Learn More