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

captcha-web-sdk

v1.0.11

Published

Captcha browser SDK with browser-global and npm import support

Readme

captcha-web-sdk 验证码前端 SDK

| 条目 | | | -------- | ------------------------------------------------------------ | | 兼容性 | Chrome、Firefox、Safari、Opera、主流手机浏览器、iOS 及 Android上的内嵌Webview | | 框架支持 | H5、Angular、React、Vue2、Vue3、Next.js、React Native(WebView) |

本地打包

  1. 安装依赖

    npm install
  2. 执行 SDK 生产打包

    npm run build
  3. 发包前检查

    npm run release:check
  4. 打包产物在 dist 目录下,核心文件如下:

    • dist/tac/js/tac.min.js
    • dist/tac/css/tac.css
    • dist/tac/images/*

作为 SDK 接入

方式一: 浏览器 script 直引

<link rel="stylesheet" href="/tac/css/tac.css" />
<script src="/tac/js/tac.min.js"></script>

<div id="captcha-box"></div>
<script>
  const tac = new TAC({
    requestCaptchaDataUrl: "/gen",
    validCaptchaUrl: "/check",
    bindEl: "#captcha-box"
  });
  tac.init();
</script>

方式二: npm 包方式引入

npm install captcha-web-sdk
import TAC, { CaptchaWebSdk, CaptchaConfig } from "captcha-web-sdk";
import "captcha-web-sdk/style.css";

const tac = new TAC({
  requestCaptchaDataUrl: "/gen",
  validCaptchaUrl: "/check",
  bindEl: "#captcha-box"
});

tac.init();

说明:

  • 默认导出为 TAC,等价于 CaptchaWebSdk
  • 仍然兼容浏览器全局变量 window.TACwindow.CaptchaConfig
  • 如果你还在使用历史的 load.min.js 初始化方式,本仓库当前打包产物依然兼容该模式

配置参数表

构造函数签名:

const tac = new TAC(config, style);

其中:

  • config 是业务配置,负责接口地址、请求头、回调函数等
  • style 是展示配置,负责按钮、背景、logo、文案和字号等

1. config 参数表

| 参数名 | 类型 | 必填 | 默认值 | 说明 | 示例 | | ------ | ---- | ---- | ------ | ---- | ---- | | bindEl | string | 是 | 无 | 验证码挂载容器的选择器,必须能被 document.querySelector 找到 | "#captcha-box" | | requestCaptchaDataUrl | string | 是 | 无 | 获取验证码数据的后端接口地址,SDK 默认用 POST + application/json 请求 | "/captcha/gen" | | validCaptchaUrl | string | 是 | 无 | 提交验证码校验结果的后端接口地址,SDK 默认用 POST + application/json 请求 | "/captcha/check" | | requestHeaders | Record<string, string> | 否 | {} | 发送到两个接口的公共请求头 | { Authorization: "Bearer xxx" } | | timeToTimestamp | boolean | 否 | true | 是否自动把请求数据中的 Date 转成时间戳 | false | | i18n | Partial<CaptchaI18nConfig> | 否 | 默认内置文案 | 运行时错误提示和状态文案覆盖配置 | { tips_error: "校验失败" } | | validSuccess | (res, captcha, tac) => void | 否 | 默认打印日志并销毁窗口 | 验证成功回调 | (res, c, tac) => tac.destroyWindow() | | validFail | (res, captcha, tac) => void | 否 | tac.reloadCaptcha() | 验证失败回调 | (res, c, tac) => tac.reloadCaptcha() | | btnRefreshFun | (event, tac) => void | 否 | tac.reloadCaptcha() | 点击刷新按钮后的回调 | (e, tac) => tac.reloadCaptcha() | | btnCloseFun | (event, tac) => void | 否 | tac.destroyWindow() | 点击关闭按钮后的回调 | (e, tac) => tac.destroyWindow() |

2. style 参数表

| 参数名 | 类型 | 必填 | 默认值 | 说明 | 示例 | | ------ | ---- | ---- | ------ | ---- | ---- | | btnUrl | string \| null | 否 | 内置 base64 按钮图 | 滑块按钮图片地址 | "https://cdn.example.com/btn.png" | | bgUrl | string \| null | 否 | 无 | 验证码弹窗背景图地址 | "https://cdn.example.com/bg.jpg" | | logoUrl | string \| null | 否 | 内置 logo | 底部 logo 地址,传 null 可隐藏 logo | null | | moveTrackMaskBgColor | string | 否 | #89d2ff | 滑动轨道填充背景色 | "#f7b645" | | moveTrackMaskBorderColor | string | 否 | #0298f8 | 滑动轨道边框颜色 | "#ef9c0d" | | i18n | Partial<CaptchaI18nConfig> | 否 | 默认内置文案 | UI 文案和字号覆盖配置 | { slider_title: "请拖动滑块" } |

3. i18n 参数表

支持 %s 占位符的参数:

  • unknown_captcha_type
  • tips_success

3.1 通用提示文案

| 参数名 | 默认值 | 用途 | | ------ | ------ | ---- | | required_bind_el | [TAC] 必须配置 [bindEl] 用于将验证码绑定到该元素上 | 缺少 bindEl 时抛出的错误文案 | | required_request_captcha_data_url | [TAC] 必须配置 [requestCaptchaDataUrl] 请求验证码接口 | 缺少生成接口地址时抛出的错误文案 | | required_valid_captcha_url | [TAC] 必须配置 [validCaptchaUrl] 验证验证码接口 | 缺少校验接口地址时抛出的错误文案 | | invalid_captcha_data | [TAC] 后台验证码接口数据错误 | 获取验证码接口返回结构异常时的错误文案 | | unknown_captcha_type | [TAC] 未知的验证码类型[%s] | 后端返回未知验证码类型时的错误文案 | | default_valid_success_log | 验证码校验成功,请重写 [config.validSuccess] 方法,用于自定义逻辑处理 | 未自定义成功回调时的默认日志文案 | | tips_success | 验证成功,耗时%s秒 | 验证成功的提示文案 | | tips_error | 验证失败,请重新尝试! | 普通失败提示文案 | | tips_4001 | 验证码已失效,请刷新后重试! | 验证码失效提示文案 | | tips_network_error | 网络异常,请稍后重试! | 网络异常提示文案 |

3.2 UI 文案与字号

| 参数名 | 默认值 | 用途 | | ------ | ------ | ---- | | modal_title | 请完成安全验证 | 弹窗头部主标题 | | modal_subtitle | 验证通过后即可继续操作 | 弹窗头部副标题 | | close_button_aria_label | 关闭验证 | 关闭按钮无障碍文案 | | slider_title | 拖动滑块完成拼图 | 历史滑块任务说明文案,当前默认 UI 不再展示,保留兼容 | | slider_action_hint | 按住滑块,拖动完成上方拼图 | 滑块验证码轨道提示文案 | | concat_title | 拖动滑块完成拼图 | 历史拼接任务说明文案,当前默认 UI 不再展示,保留兼容 | | concat_action_hint | 按住滑块,拖动完成上方拼图 | 拼接验证码轨道提示文案 | | image_click_title | 请依次点击: | 点选验证码标题 | | image_click_confirm_text | 确定 | 点选验证码确认按钮文案 | | rotate_title | 拖动滑块完成拼图 | 历史旋转任务说明文案,当前默认 UI 不再展示,保留兼容 | | rotate_action_hint | 按住滑块,旋转至正确角度 | 旋转验证码轨道提示文案 | | disable_title | 当前验证码不可用 | 禁用态标题 | | disable_default_message | 接口异常 | 禁用态默认提示 | | slider_title_size | 15px | 滑块验证码标题字号 | | concat_title_size | 15px | 拼接验证码标题字号 | | image_click_title_size | 20px | 点选验证码标题字号 | | rotate_title_size | 15px | 旋转验证码标题字号 | | disable_title_size | 15px | 禁用态标题字号 |

3.3 已废弃但兼容保留的 i18n 字段

| 参数名 | 当前状态 | 说明 | | ------ | -------- | ---- | | close_text | 已废弃,但仍兼容 | 会自动映射到 close_button_aria_label,建议改用新字段 | | refresh_text | 已废弃,当前忽略 | 刷新按钮已改为纯 icon 交互,不再显示该文案 |

4. 高级能力: 请求链 requestChain

如果你要在请求前后统一加签名、改请求体、打印日志,可以使用 CaptchaConfig 实例上的请求链能力。

| 方法名 | 参数 | 说明 | | ------ | ---- | ---- | | addRequestChain(chain) | { preRequest?, postRequest? } | 在链尾追加一个处理器 | | insertRequestChain(index, chain) | index, chain | 在指定位置插入处理器 | | removeRequestChain(index) | index | 删除指定位置的处理器 |

请求链回调签名:

| 回调 | 签名 | 说明 | | ---- | ---- | ---- | | preRequest | (type, requestParam, config, captcha, tac) => boolean \| void | 请求发送前执行,可修改 requestParam | | postRequest | (type, requestParam, response, config, captcha, tac) => boolean \| void | 请求完成后执行,可统一处理返回结果 |

type 可能值:

  • requestCaptchaData
  • validCaptcha

requestParam 结构:

{
  url: "/captcha/gen",
  method: "POST",
  headers: {
    "Content-Type": "application/json;charset=UTF-8"
  },
  data: {}
}

5. 最小可用配置

import TAC from "captcha-web-sdk";
import "captcha-web-sdk/style.css";

const tac = new TAC({
  bindEl: "#captcha-box",
  requestCaptchaDataUrl: "/captcha/gen",
  validCaptchaUrl: "/captcha/check"
});

tac.init();

6. 完整配置示例

import TAC from "captcha-web-sdk";
import "captcha-web-sdk/style.css";

const tac = new TAC(
  {
    bindEl: "#captcha-box",
    requestCaptchaDataUrl: "/captcha/gen",
    validCaptchaUrl: "/captcha/check",
    requestHeaders: {
      Authorization: "Bearer your-token"
    },
    timeToTimestamp: true,
    i18n: {
      tips_error: "验证失败,请重新再试一次",
      tips_network_error: "网络开小差了,请稍后重试"
    },
    validSuccess: (res, captcha, tacInstance) => {
      tacInstance.destroyWindow();
      console.log("校验成功:", res);
    },
    validFail: (res, captcha, tacInstance) => {
      tacInstance.reloadCaptcha();
    },
    btnRefreshFun: (event, tacInstance) => {
      tacInstance.reloadCaptcha();
    },
    btnCloseFun: (event, tacInstance) => {
      tacInstance.destroyWindow();
    }
  },
  {
    logoUrl: null,
    btnUrl: "https://cdn.example.com/captcha/btn.png",
    bgUrl: "https://cdn.example.com/captcha/bg.jpg",
    moveTrackMaskBgColor: "#f7b645",
    moveTrackMaskBorderColor: "#ef9c0d",
    i18n: {
      slider_title: "拖动滑块完成验证",
      slider_action_hint: "向右拖动完成验证",
      modal_title: "请完成下列验证后继续",
      modal_subtitle: "验证成功后会自动返回当前流程",
      close_button_aria_label: "关闭验证码弹窗",
      image_click_confirm_text: "确认"
    }
  }
);

tac.init();

国际化配置

现在支持两种国际化覆盖方式:

  • config.i18n: 适合接口提示、运行时错误等文案
  • style.i18n: 适合按钮、标题、禁用态等 UI 文案

两者都会和默认文案自动合并,style.i18n 优先级最高。

import TAC from "captcha-web-sdk";
import "captcha-web-sdk/style.css";

const tac = new TAC(
  {
    requestCaptchaDataUrl: "/gen",
    validCaptchaUrl: "/check",
    bindEl: "#captcha-box",
    i18n: {
      required_bind_el: "[TAC] bindEl is required",
      required_request_captcha_data_url: "[TAC] requestCaptchaDataUrl is required",
      required_valid_captcha_url: "[TAC] validCaptchaUrl is required",
      invalid_captcha_data: "[TAC] Invalid captcha payload",
      unknown_captcha_type: "[TAC] Unknown captcha type[%s]",
      tips_success: "Verified in %s seconds",
      tips_error: "Verification failed, please try again",
      tips_4001: "Captcha expired, please refresh and retry",
      tips_network_error: "Network error, please try again later"
    },
    validSuccess: (res, c, tacInstance) => {
      tacInstance.destroyWindow();
      console.log("captcha ok", res);
    }
  },
  {
    i18n: {
      modal_title: "Please complete the verification",
      modal_subtitle: "Continue after the verification passes",
      close_button_aria_label: "Close verification",
      slider_title: "Drag the slider to complete the puzzle",
      slider_action_hint: "Hold the handle and drag to complete the puzzle",
      concat_title: "Drag the slider to complete the puzzle",
      concat_action_hint: "Hold the handle and drag to complete the puzzle",
      image_click_title: "Click in order:",
      image_click_confirm_text: "Confirm",
      rotate_title: "Drag the slider to rotate",
      rotate_action_hint: "Hold the handle and rotate to the correct angle",
      disable_title: "Captcha unavailable",
      disable_default_message: "Request failed"
    }
  }
);

tac.init();

最近变更

本次 SDK UI 与国际化做了以下调整:

  • 统一滑块类验证码的信息层级:头部 modal_title / modal_subtitle 作为主标题区,内部 slider_title / concat_title / rotate_title 调整为图片区上方的任务说明
  • 重做 SLIDER / CONCAT / ROTATE 三类滑块轨道,统一为更接近系统控件的浅底轨道、实体把手和完整蓝色进度底块
  • 滑块类验证码已移除图片区上方的额外任务说明行,避免与头部主标题重复;slider_title / concat_title / rotate_title 当前仅兼容保留
  • 新增弹窗头部文案国际化:modal_titlemodal_subtitle
  • 新增关闭按钮无障碍文案国际化:close_button_aria_label
  • 新增滑块轨道提示国际化:slider_action_hintconcat_action_hintrotate_action_hint
  • 刷新按钮调整为纯 icon 形式,refresh_text 不再展示
  • 刷新按钮点击时增加旋转动画反馈
  • 关闭按钮与刷新按钮都改为纯 icon 交互样式
  • 弹窗整体圆角和字号已收敛,视觉更贴近用户端业务场景

兼容性说明:

  • 旧字段 close_text 仍会自动兼容到 close_button_aria_label
  • 旧字段 refresh_text 不会报错,但当前 UI 已不再使用该文案

多框架示例

完整示例见 examples/frameworks.md

  • Next.js: 仅在 Client Component 中初始化,CSS 放到 app/layout.tsxpages/_app.tsx
  • React: 在 useEffect 中初始化,在清理函数里销毁
  • Vue3: 在 onMounted 中初始化,在 onBeforeUnmount 中销毁
  • Vue2: 在 mounted 中初始化,在 beforeDestroy 中销毁
  • React Native: 通过 react-native-webview 加载 H5 页面或内联 HTML,不支持直接在原生运行时中挂载 DOM 版 SDK

发布到 npm

首次发布前

  1. 登录 npm

    npm login
  2. 确认包名还未被占用

    npm view captcha-web-sdk version

    如果返回 404 Not Found,说明当前包名还没有被注册。

  3. 执行发包前检查

    npm run release:check

手动发布

npm publish

CI 自动发布

仓库内已提供 GitHub Actions 工作流:

  • 推送 v* 标签时自动发布
  • 也支持手动触发 workflow_dispatch

如果你的源码仓库托管在 Gitee,.github/workflows 不会自动执行,需要将同样的步骤迁移到 Gitee Go 或其他 CI 平台。

使用前需要在仓库 Secrets 中配置:

  • NPM_TOKEN

示例发布命令:

git tag v1.0.0
git push origin v1.0.0

旧版 load.min.js 兼容接入

如果你还在使用历史初始化方式,也可以继续通过 window.initTAC 接入。推荐优先迁移到上文的 npm / new TAC(...) 方式,便于类型提示、打包优化和长期维护。

<div id="captcha-box"></div>
<script src="/tac/load.min.js"></script>
<script>
  const config = {
    requestCaptchaDataUrl: "/gen",
    validCaptchaUrl: "/check",
    bindEl: "#captcha-box",
    i18n: {
      tips_error: "验证失败,请重试"
    }
  };

  const style = {
    logoUrl: null,
    i18n: {
      modal_title: "请完成安全验证",
      modal_subtitle: "验证通过后即可继续操作",
      close_button_aria_label: "关闭验证",
      slider_action_hint: "按住滑块,拖动完成上方拼图"
    }
  };

  window.initTAC("/tac", config, style).then((tac) => {
    tac.init();
  });
</script>