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 🙏

© 2026 – Pkg Stats / Ryan Hefner

@smallcaomei/usekit

v1.0.0

Published

The missing React hooks toolkit — a collection of essential, type-safe, SSR-friendly hooks. Zero dependencies, fully tree-shakeable.

Readme

⚡ usekit

你一直缺的 React Hooks 工具库。

32 个面向真实业务、类型完备、SSR 安全的 React Hooks —— 零依赖,体积极小。

npm version bundle size CI types license PRs welcome

🚀 在线演示 · English · 简体中文


为什么选择 usekit?

  • 🪶 零运行时依赖 —— 除了 React(>=16.8)什么都不需要。
  • 🌳 完全可 Tree-shaking —— "sideEffects": false,用多少打包多少。
  • 🔒 类型安全 —— 严格 TypeScript 编写,类型声明随包发布。
  • 🖥️ SSR 安全 —— 每个 Hook 都对 window/document 的缺失做了防护。
  • 🧪 经过测试 —— 由 Vitest + Testing Library 测试套件覆盖。
  • 📦 ESM + CJS 双格式 —— 从 Next.js 到 Vite 再到纯 Node 都能用。

安装

npm install @smallcaomei/usekit
# 或
pnpm add @smallcaomei/usekit
# 或
yarn add @smallcaomei/usekit

快速上手

import { useDebounce, useLocalStorage, useToggle } from "@smallcaomei/usekit";

function SearchBox() {
  const [query, setQuery] = useLocalStorage("last-query", "");
  const debounced = useDebounce(query, 300);
  const [open, { toggle }] = useToggle(false);

  // `debounced` 会在用户停止输入 300ms 后才更新。
  return (
    <input value={query} onChange={(e) => setQuery(e.target.value)} />
  );
}

Hooks 一览

👉 实时交互演示 → —— 每个演示都由真实的库驱动。

状态

| Hook | 说明 | | --- | --- | | useToggle | 布尔状态,附带 toggle / setTrue / setFalse。 | | useCounter | 数值状态,支持 inc / dec / reset 与 min/max 钳制。 | | useList | 不可变数组操作:pushremoveAtsortfilter…… | | usePrevious | 上一次渲染的值。 | | useLatest | 始终持有最新值的 ref。 |

存储

| Hook | 说明 | | --- | --- | | useLocalStorage | 持久化状态,支持跨标签页同步。 | | useSessionStorage | 会话级持久化状态。 | | useDarkMode | 跟随系统并持久化的深色模式。 |

时序

| Hook | 说明 | | --- | --- | | useDebounce | 对值做防抖。 | | useDebouncedCallback | 防抖函数,带 cancel() / flush()。 | | useThrottle | 对值做节流。 | | useInterval | 声明式 setInterval(传 null 暂停)。 | | useTimeout | 声明式 setTimeout。 |

生命周期

| Hook | 说明 | | --- | --- | | useMount | 挂载时执行一次回调。 | | useUnmount | 卸载时执行回调。 | | useUpdateEffect | 跳过首次渲染的 useEffect。 | | useIsomorphicLayoutEffect | SSR 安全的 useLayoutEffect。 |

浏览器与视口

| Hook | 说明 | | --- | --- | | useMediaQuery | 响应式匹配 CSS 媒体查询。 | | useWindowSize | 追踪窗口内部尺寸。 | | useElementSize | 用 ResizeObserver 测量元素。 | | useIntersectionObserver | 观察元素可见性(懒加载、滚动揭示)。 | | useCopyToClipboard | 复制文本,自带优雅降级。 | | useNetworkState | 在线/离线 + 连接质量。 | | useGeolocation | 追踪用户地理位置。 | | useScrollLock | 为弹窗/抽屉锁定页面滚动。 | | useDocumentTitle | 同步 document.title。 |

事件

| Hook | 说明 | | --- | --- | | useEventListener | 强类型声明式 addEventListener。 | | useClickOutside | 检测元素外部点击。 | | useHover | 通过 ref 追踪悬停状态。 | | useKeyPress | 响应按键与组合键(如 ⌘K)。 | | useIdle | 检测用户空闲。 |

数据

| Hook | 说明 | | --- | --- | | useFetch | 轻量数据请求,含 loading/error 状态、取消与重取。 |

示例

import { useKeyPress } from "@smallcaomei/usekit";

function App() {
  const [open, setOpen] = useState(false);
  useKeyPress("k", () => setOpen(true), {
    modifiers: { meta: true }, // ⌘K
    preventDefault: true,
  });
  return open ? <CommandPalette onClose={() => setOpen(false)} /> : null;
}
import { useRef, useState } from "react";
import { useClickOutside } from "@smallcaomei/usekit";

function Dropdown() {
  const [open, setOpen] = useState(false);
  const ref = useRef<HTMLDivElement>(null);
  useClickOutside(ref, () => setOpen(false));
  return open ? <div ref={ref}>…菜单…</div> : null;
}
import { useIntersectionObserver } from "@smallcaomei/usekit";

function LazyImage({ src, alt }: { src: string; alt: string }) {
  const { ref, isIntersecting } = useIntersectionObserver({
    freezeOnceVisible: true,
  });
  return <img ref={ref} src={isIntersecting ? src : undefined} alt={alt} />;
}

SSR 与 Next.js

所有 Hooks 都是服务端安全的。仅浏览器可用的 Hooks(useWindowSizeuseMediaQuery 等) 会在服务端返回合理的默认值,并在客户端水合,因此不会出现引用错误或水合不一致。

本地开发

npm install          # 安装依赖
npm run build        # 用 tsup 构建库(ESM + CJS + d.ts)
npm test             # 运行 Vitest 测试
npm run typecheck    # 仅做类型检查
npm run demo         # 在 localhost:5173 启动交互演示

参与贡献

非常欢迎 PR!新增一个 Hook 很简单 —— 详见 CONTRIBUTING.md

许可证

MIT © usekit contributors