{"_id":"@3-/plimit","_rev":"2-bc92154d31c0976196a0ba48ee217432","name":"@3-/plimit","dist-tags":{"latest":"0.1.3"},"versions":{"0.1.2":{"name":"@3-/plimit","version":"0.1.2","keywords":["concurrency","limit","promise","async","queue"],"author":{"name":"i18n.site@gmail.com"},"license":"MulanPSL-2.0","_id":"@3-/plimit@0.1.2","maintainers":[{"name":"i18n-now","email":"i18n.site@gmail.com"}],"homepage":"https://github.com/i18n-site/lib/tree/dev/plimit","bugs":{"url":"https://github.com/i18n-site/lib/issues"},"dist":{"shasum":"2c7ac4d4c906a6af5922f6978b49b1981b6c98cc","tarball":"https://registry.npmjs.org/@3-/plimit/-/plimit-0.1.2.tgz","fileCount":3,"integrity":"sha512-rrcEWZP1qnVMaizCLO4i+ZZKDh1Kuh4APegyJCrdLOnr0810GdWVg5xumtzmpFrD8w1gAtW9S1ZZq0xzt5cUpg==","signatures":[{"sig":"MEQCIFVICHenbjb9ZK25TB/ywMAGshKNizVs2uz0lloz1uEnAiBOku80MR2NhFcfZdIPiYKnyUdfMVbSYw9GROyRpfqJmA==","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"unpackedSize":7664},"type":"module","exports":{".":"./lib.js","./*":"./*"},"gitHead":"cc91e83b7ad11881e663a8625d8bd8f1d74d8d32","scripts":{},"_npmUser":{"name":"i18n-now","email":"i18n.site@gmail.com"},"repository":{"url":"git+https://github.com/i18n-site/lib.git","type":"git"},"_npmVersion":"11.13.0","description":"Concurrency limit for async functions / 异步函数并发控制","directories":{},"_nodeVersion":"26.2.0","_hasShrinkwrap":false,"devDependencies":{},"_npmOperationalInternal":{"tmp":"tmp/plimit_0.1.2_1780436505455_0.7341730748178823","host":"s3://npm-registry-packages-npm-production"}},"0.1.3":{"name":"@3-/plimit","version":"0.1.3","keywords":["concurrency","limit","promise","async","queue"],"description":"Concurrency limit for async functions / 异步函数并发控制","repository":{"type":"git","url":"git+https://github.com/i18n-site/lib.git"},"homepage":"https://github.com/i18n-site/lib/tree/dev/plimit","author":{"name":"i18n.site@gmail.com"},"license":"MulanPSL-2.0","exports":{".":"./lib.js","./*":"./*"},"devDependencies":{},"scripts":{},"type":"module","gitHead":"54cbddf9f96d9364596b28c11463a8685fcc3856","_id":"@3-/plimit@0.1.3","bugs":{"url":"https://github.com/i18n-site/lib/issues"},"_nodeVersion":"26.2.0","_npmVersion":"11.13.0","dist":{"integrity":"sha512-kzoZ7NdplML8Tyrd7Fr9knHs8t/t3ULuw7KbFq46apGevN7q1Pn6v/jQjdjpalwpN51HcvgSB4LgXeZLOXAvxA==","shasum":"b76923e52d8baf5d0bc95eba6ddc1474b7647d6a","tarball":"https://registry.npmjs.org/@3-/plimit/-/plimit-0.1.3.tgz","fileCount":3,"unpackedSize":7664,"signatures":[{"keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U","sig":"MEUCIQDQqGxlJ3S/vDkPayxjz8wvGNvpS6b4vqAEI7XDssXykgIgE5W7gx0rjCb2xn6xtF9pMjx9va3E9ihMiWEfSiNbFDI="}]},"_npmUser":{"name":"i18n-now","email":"i18n.site@gmail.com"},"directories":{},"maintainers":[{"name":"i18n-now","email":"i18n.site@gmail.com"}],"_npmOperationalInternal":{"host":"s3://npm-registry-packages-npm-production","tmp":"tmp/plimit_0.1.3_1780436533665_0.7633210960103722"},"_hasShrinkwrap":false}},"time":{"created":"2026-06-02T21:41:45.300Z","modified":"2026-06-02T21:42:13.909Z","0.1.2":"2026-06-02T21:41:45.637Z","0.1.3":"2026-06-02T21:42:13.797Z"},"bugs":{"url":"https://github.com/i18n-site/lib/issues"},"author":{"name":"i18n.site@gmail.com"},"license":"MulanPSL-2.0","homepage":"https://github.com/i18n-site/lib/tree/dev/plimit","keywords":["concurrency","limit","promise","async","queue"],"repository":{"type":"git","url":"git+https://github.com/i18n-site/lib.git"},"description":"Concurrency limit for async functions / 异步函数并发控制","maintainers":[{"name":"i18n-now","email":"i18n.site@gmail.com"}],"readme":"[English](#en) | [中文](#zh)\n\n---\n\n<a id=\"en\"></a>\n# @3-/plimit : Concurrency Limit for Async Functions\n\n## Table of Contents\n- [Introduction](#introduction)\n- [Installation](#installation)\n- [Usage Demo](#usage-demo)\n- [Design & Architecture](#design--architecture)\n- [Directory Structure](#directory-structure)\n- [Tech Stack](#tech-stack)\n- [History & Trivia](#history--trivia)\n\n## Introduction\n`@3-/plimit` restricts the concurrency of asynchronous operations. It runs tasks under a specified concurrency threshold, queuing subsequent tasks until active slots become available.\n\n## Installation\nInstall using `bun`:\n```bash\nbun i @3-/plimit\n```\n\n## Usage Demo\nImport the package, initialize a limiter with the maximum concurrency, and wrap asynchronous functions.\n\n```javascript\nimport pLimit from \"@3-/plimit\";\n\n// Initialize concurrency limit of 2\nconst limit = pLimit(2);\n\nconst tasks = [\n  limit(() => fetch(\"https://api.example.com/data/1\")),\n  limit(() => fetch(\"https://api.example.com/data/2\")),\n  limit(() => fetch(\"https://api.example.com/data/3\")),\n];\n\n// Resolves when all tasks complete under concurrency limit\nconst results = await Promise.all(tasks);\n```\n\n## Design & Architecture\nThe limiter maintains an internal task queue. When a task is added:\n1. It is pushed into the queue with its promise resolution callbacks.\n2. The controller checks if the number of active tasks is below the limit.\n3. If below the limit, the next task is dequeued, and its execution begins.\n4. When a task resolves or rejects, the active count decrements, and the queue processes the next task.\n\nBelow is the execution flow of the concurrency limiter:\n\n```mermaid\ngraph TD\n    A[Task Wrapper Called] --> B{Active Count < Limit?}\n    B -- Yes --> C[Increment Active Count]\n    C --> D[Execute Async Function]\n    D --> E[Resolve/Reject Promise]\n    E --> F[Decrement Active Count]\n    F --> G[Trigger Next Task]\n    B -- No --> H[Queue Task]\n    H --> G\n```\n\n## Directory Structure\n```\n.\n├── src/\n│   └── lib.js      # Core concurrency limiting logic\n└── test/\n    └── main.test.js # Unit tests and usage examples\n```\n\n## Tech Stack\n- **JavaScript (ES Modules)**: Core implementation language.\n- **Bun**: Test runner and dependency management.\n\n## History & Trivia\nThe concept of limiting concurrency traces back to the early days of concurrent computing. In the early 1960s, Dutch computer scientist Edsger W. Dijkstra introduced the concept of the \"semaphore\" to solve synchronization issues in the THE multiprogramming system. \n\nA semaphore acts as a variable that controls access to a common resource by multiple processes. The concurrency limit implementation in `@3-/plimit` is structurally equivalent to Dijkstra's counting semaphore, where the capacity represents the limit, and the queue coordinates task scheduling.\n\n---\n\n<a id=\"zh\"></a>\n# @3-/plimit : 异步函数并发控制\n\n## 目录\n- [功能介绍](#功能介绍)\n- [安装](#安装)\n- [使用演示](#使用演示)\n- [设计思路](#设计思路)\n- [目录结构](#目录结构)\n- [技术堆栈](#技术堆栈)\n- [历史小故事](#历史小故事)\n\n## 功能介绍\n`@3-/plimit` 限制异步操作并发量。此模块确保在设定的并发阈值下执行任务，并将超出限制的任务排队，直到腾出可用槽位。\n\n## 安装\n使用 `bun` 安装：\n```bash\nbun i @3-/plimit\n```\n\n## 使用演示\n导入模块，设置最大并发数初始化限制器，包裹异步函数执行。\n\n```javascript\nimport pLimit from \"@3-/plimit\";\n\n// 初始化并发限制为 2\nconst limit = pLimit(2);\n\nconst tasks = [\n  limit(() => fetch(\"https://api.example.com/data/1\")),\n  limit(() => fetch(\"https://api.example.com/data/2\")),\n  limit(() => fetch(\"https://api.example.com/data/3\")),\n];\n\n// 并发限制下执行，所有任务完成时返回结果\nconst results = await Promise.all(tasks);\n```\n\n## 设计思路\n限制器内部维护任务队列。任务加入时：\n1. 任务及对应的 Promise 回调存入队列。\n2. 控制器检测当前活动任务数是否小于设定的并发限制。\n3. 若小于限制，从队列头部取出任务并开始执行。\n4. 任务执行完毕（无论成功或失败），递减活动任务数，并触发下一次调度。\n\n下面是并发限制器的调用流程图：\n\n```mermaid\ngraph TD\n    A[调用限制器包装函数] --> B{活动任务数 < 限制值?}\n    B -- 是 --> C[增加活动任务数]\n    C --> D[执行异步函数]\n    D --> E[完成或捕获异常]\n    E --> F[减少活动任务数]\n    F --> G[触发执行下一任务]\n    B -- 否 --> H[任务入队等待]\n    H --> G\n```\n\n## 目录结构\n```\n.\n├── src/\n│   └── lib.js      # 核心并发限制逻辑\n└── test/\n    └── main.test.js # 单元测试与演示代码\n```\n\n## 技术堆栈\n- **JavaScript (ES Modules)**: 核心逻辑语言。\n- **Bun**: 测试运行器及依赖管理。\n\n## 历史小故事\n并发限制的概念源于早期并发计算。20世纪60年代初，荷兰计算机科学家艾兹赫尔·戴克斯特拉（Edsger W. Dijkstra）在设计 THE 多道程序设计系统时，提出了“信号量（Semaphore）”概念，用于解决多进程同步问题。\n\n信号量用于控制多个进程对共享资源的访问。`@3-/plimit` 实现的并发限制器，在结构上相当于戴克斯特拉提出的计数信号量（Counting Semaphore）。限制值即信号量初始容量，队列负责协调任务调度。\n\n---\n\n## About\n\nThis project is an open-source component of [i18n.site ⋅ Internationalization Solution](https://i18n.site).\n\n* [i18 : MarkDown Command Line Translation Tool](https://i18n.site/i18)\n\n  The translation perfectly maintains the Markdown format.\n\n  It recognizes file changes and only translates the modified files.\n\n  The translated Markdown content is editable; if you modify the original text and translate it again, manually edited translations will not be overwritten (as long as the original text has not been changed).\n\n* [i18n.site : MarkDown Multi-language Static Site Generator](https://i18n.site/i18n.site)\n\n  Optimized for a better reading experience\n\n## 关于\n\n本项目为 [i18n.site ⋅ 国际化解决方案](https://i18n.site) 的开源组件。\n\n* [i18 :  MarkDown命令行翻译工具](https://i18n.site/i18)\n\n  翻译能够完美保持 Markdown 的格式。能识别文件的修改，仅翻译有变动的文件。\n\n  Markdown 翻译内容可编辑；如果你修改原文并再次机器翻译，手动修改过的翻译不会被覆盖（如果这段原文没有被修改）。\n\n* [i18n.site : MarkDown多语言静态站点生成器](https://i18n.site/i18n.site) 为阅读体验而优化。\n","readmeFilename":"README.md"}