pax_global_header00006660000000000000000000000064151556112550014520gustar00rootroot0000000000000052 comment=90f047e75a0fed0f7c2be1a7d195a805e4d605d4 nanoid-5.1.7/000077500000000000000000000000001515561125500130025ustar00rootroot00000000000000nanoid-5.1.7/.editorconfig000066400000000000000000000002751515561125500154630ustar00rootroot00000000000000root = true [*] indent_style = space indent_size = 2 end_of_line = lf charset = utf-8 trim_trailing_whitespace = true insert_final_newline = true [nanoid.js] insert_final_newline = false nanoid-5.1.7/.github/000077500000000000000000000000001515561125500143425ustar00rootroot00000000000000nanoid-5.1.7/.github/FUNDING.yml000066400000000000000000000000401515561125500161510ustar00rootroot00000000000000tidelift: npm/nanoid github: ai nanoid-5.1.7/.github/workflows/000077500000000000000000000000001515561125500163775ustar00rootroot00000000000000nanoid-5.1.7/.github/workflows/jsr.yml000066400000000000000000000012511515561125500177170ustar00rootroot00000000000000name: Publish to JSR on: push: tags: - '*' permissions: contents: read id-token: write jobs: jsr: runs-on: ubuntu-latest steps: - name: Checkout the repository uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2 - name: Check tag version id: check run: | TAG=${GITHUB_REF#refs/tags/} MAJOR=$(echo $TAG | cut -d. -f1) if [[ "$MAJOR" =~ ^[0-9]+$ && "$MAJOR" -gt 3 ]]; then echo "version_ok=true" >> $GITHUB_OUTPUT fi shell: bash - name: Publish to JSR if: steps.check.outputs.version_ok == 'true' run: npx jsr publish nanoid-5.1.7/.github/workflows/release.yml000066400000000000000000000027071515561125500205500ustar00rootroot00000000000000name: Release on: push: tags: - '*' permissions: contents: write jobs: release: name: Release On Tag if: startsWith(github.ref, 'refs/tags/') runs-on: ubuntu-latest steps: - name: Checkout the repository uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2 - name: Extract the changelog id: changelog run: | TAG_NAME=${GITHUB_REF/refs\/tags\//} READ_SECTION=false CHANGELOG="" while IFS= read -r line; do if [[ "$line" =~ ^#+\ +(.*) ]]; then if [[ "${BASH_REMATCH[1]}" == "$TAG_NAME" ]]; then READ_SECTION=true elif [[ "$READ_SECTION" == true ]]; then break fi elif [[ "$READ_SECTION" == true ]]; then CHANGELOG+="$line"$'\n' fi done < "CHANGELOG.md" CHANGELOG=$(echo "$CHANGELOG" | awk '/./ {$1=$1;print}') echo "changelog_content<> $GITHUB_OUTPUT echo "$CHANGELOG" >> $GITHUB_OUTPUT echo "EOF" >> $GITHUB_OUTPUT - name: Create the release if: steps.changelog.outputs.changelog_content != '' uses: softprops/action-gh-release@1853d73993c8ca1b2c9c1a7fede39682d0ab5c2a # v2.5.3 with: name: ${{ github.ref_name }} body: '${{ steps.changelog.outputs.changelog_content }}' draft: false prerelease: false nanoid-5.1.7/.github/workflows/test.yml000066400000000000000000000042751515561125500201110ustar00rootroot00000000000000name: Test on: push: branches: - main - v3 pull_request: permissions: contents: read jobs: full: name: Node.js Latest Full runs-on: ubuntu-latest steps: - name: Checkout the repository uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2 - name: Install pnpm uses: pnpm/action-setup@fc06bc1257f339d1d5d8b3a19a8cae5388b55320 # v4.4.0 with: version: 10 - name: Install Node.js uses: actions/setup-node@53b83947a5a98c8d113130e565377fae1a50d02f # v6.3.0 with: node-version: 25 cache: pnpm - name: Install dependencies run: pnpm install --ignore-scripts - name: Run tests run: pnpm test short: runs-on: ubuntu-latest strategy: matrix: node-version: - 24 - 22 - 20 - 18 name: Node.js ${{ matrix.node-version }} Quick steps: - name: Checkout the repository uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2 - name: Install pnpm uses: pnpm/action-setup@fc06bc1257f339d1d5d8b3a19a8cae5388b55320 # v4.4.0 with: version: 10 - name: Install Node.js ${{ matrix.node-version }} uses: actions/setup-node@53b83947a5a98c8d113130e565377fae1a50d02f # v6.3.0 with: node-version: ${{ matrix.node-version }} cache: pnpm - name: Install dependencies run: pnpm install --ignore-scripts - name: Run unit tests run: pnpm bnt benchmark: name: Benchmark runs-on: ubuntu-latest steps: - name: Checkout the repository uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2 - name: Install pnpm uses: pnpm/action-setup@fc06bc1257f339d1d5d8b3a19a8cae5388b55320 # v4.4.0 with: version: 10 - name: Install Node.js uses: actions/setup-node@53b83947a5a98c8d113130e565377fae1a50d02f # v6.3.0 with: node-version: 22 cache: pnpm - name: Install dependencies run: pnpm install --ignore-scripts - name: Run benchmark run: node ./test/benchmark.js nanoid-5.1.7/.gitignore000066400000000000000000000000311515561125500147640ustar00rootroot00000000000000node_modules/ coverage/ nanoid-5.1.7/.npmignore000066400000000000000000000000561515561125500150020ustar00rootroot00000000000000test/ tsconfig.json coverage/ img/ jsr.json nanoid-5.1.7/.prettierignore000066400000000000000000000000121515561125500160360ustar00rootroot00000000000000nanoid.js nanoid-5.1.7/CHANGELOG.md000066400000000000000000000200051515561125500146100ustar00rootroot00000000000000# Change Log This project adheres to [Semantic Versioning](http://semver.org/). ## 5.1.7 * Added `--version` to CLI (by @mahmoodhamdi). * Updated `nanoid.js` for CDN (by @mahmoodhamdi). * Fixed docs (by @mahmoodhamdi). * Fixed `customRandom` types (by @oguimbal). ## 5.1.6 * Fixed infinite loop on 0 size for `customAlphabet`. ## 5.1.5 * Fixed latest version on npm after 3.x release. ## 5.1.4 * Fixed latest version on npm after 3.x release. ## 5.1.3 * Fixed React Native support (by @steida). ## 5.1.2 * Fixed module docs. ## 5.1.1 * Fixed opaque types support for non-secure generator. * Added JSR support. ## 5.1.0 * Added opaque types support (by @kossnocorp). ## 5.0.9 * Fixed a way to break Nano ID by passing non-integer size (by @myndzi). ## 5.0.8 * Reduced `customAlphabet` size (by @kirillgroshkov). ## 5.0.7 * Fixed Parcel support (by @WilhelmYakunin). ## 5.0.6 * Fixed React Native support. ## 5.0.5 * Make browser’s version faster by increasing size a little (by Samuel Elgozi). ## 5.0.4 * Fixed CLI docs (by @ilyaboka). ## 5.0.3 * Fixed CLI docs (by Chris Schmich). ## 5.0.2 * Fixed `webcrypto` import (by Divyansh Singh). ## 5.0.1 * Fixed Node.js 18 support. ## 5.0 * Moved Node.js version to Web Crypto API. * Removed async API since Web Crypto API has only sync version. * Removed Node.js 14 and 16 support. ## 4.0.2 * Added [link](https://github.com/sponsors/ai) to Github Sponsors. ## 4.0.1 * Reduced npm package size (by @HiChen404). ## 4.0 * Removed CommonJS support. Nano ID 4 will work only with ESM applications. We will support 3.x branch with CommonJS for users who can’t migrate to ESM. * Removed Node.js 10 and Node.js 12 support. * Reduced npm package size. ## 3.3.11 * Fixed React Native support. ## 3.3.10 * Fixed React Native support (by @steida). ## 3.3.9 * Reduced npm package size. ## 3.3.8 * Fixed a way to break Nano ID by passing non-integer size (by @myndzi). ## 3.3.7 * Fixed `node16` TypeScript support (by Saadi Myftija). ## 3.3.6 * Fixed package. ## 3.3.5 * Backport funding information. ## 3.3.4 * Fixed `--help` in CLI (by @Lete114). ## 3.3.3 * Reduced size (by Anton Khlynovskiy). ## 3.3.2 * Fixed `enhanced-resolve` support. ## 3.3.1 * Reduced package size. ## 3.3 * Added `size` argument to function from `customAlphabet` (by Stefan Sundin). ## 3.2 * Added `--size` and `--alphabet` arguments to binary (by Vitaly Baev). ## 3.1.32 * Reduced `async` exports size (by Artyom Arutyunyan). * Moved from Jest to uvu (by Vitaly Baev). ## 3.1.31 * Fixed collision vulnerability on object in `size` (by Artyom Arutyunyan). ## 3.1.30 * Reduced size for project with `brotli` compression (by Anton Khlynovskiy). ## 3.1.29 * Reduced npm package size. ## 3.1.28 * Reduced npm package size. ## 3.1.27 * Cleaned `dependencies` from development tools. ## 3.1.26 * Improved performance (by Eitan Har-Shoshanim). * Reduced npm package size. ## 3.1.25 * Fixed `browserify` support. ## 3.1.24 * Fixed `browserify` support (by Artur Paikin). ## 3.1.23 * Fixed `esbuild` support. ## 3.1.22 * Added `default` and `browser.default` to `package.exports`. ## 3.1.21 * Reduced npm package size. ## 3.1.20 * Fix ES modules support. ## 3.1.19 * Reduced `customAlphabet` size (by Enrico Scherlies). ## 3.1.18 * Fixed `package.exports`. ## 3.1.17 * Added files without `process`. ## 3.1.16 * Speeded up Nano ID 4 times (by Peter Boyer). ## 3.1.15 * Fixed `package.types` path. ## 3.1.14 * Added `package.types`. ## 3.1.13 * Removed Node.js 15.0.0 with `randomFillSync` regression from `engines.node`. ## 3.1.12 * Improved IE 11 docs. ## 3.1.11 * Fixed asynchronous `customAlphabet` in browser (by @LoneRifle). ## 3.1.10 * Fix ES modules support. ## 3.1.9 * Try to fix React Native Expo support. ## 3.1.8 * Add React Native Expo support. ## 3.1.7 * Clean up code. ## 3.1.6 * Avoid `self` using. ## 3.1.5 * Improve IE docs and warning. ## 3.1.4 * Restrict old Node.js 13 by `engines.node` (by Cansin Yildiz). ## 3.1.3 * Fix ES modules issue with CLI. ## 3.1.2 * Add shebang to CLI. ## 3.1.1 * Fix CLI. ## 3.1 * Add `npx nanoid` CLI. ## 3.0.2 * Fix docs (by Dylan Irlbeck ). ## 3.0.1 * Fix React Native warning on `non-secure` import (by Jia Huang). ## 3.0 **Migration guide:** * Move to ES2016 syntax. You need to use Babel for IE 11. * Move to named exports `import { nanoid } from 'nanoid'`. * Move `import url from 'nanoid/url'` to `import { urlAlphabet } from 'nanoid'`. * Replace `format()` to `customRandom()`. * Replace `generate()` to `customAlphabet()`. * Remove `async/format`. * Remove React Native support for `nanoid/async`. * Add `nanoid.js` to use directly in browser from CDN. * Add TypeScript type definitions. * Add ES modules support for bundlers, Node.js, and React Native. * Fix React Native support. * Reduce size. * Improve docs (by Dair Aidarkhanov). ## 2.1.11 * Reduce size (by Anton Evzhakov). ## 2.1.10 * Reduce size by 10% (by Anton Khlynovskiy). ## 2.1.9 * Reduce `format` and `async/format` size (by Dair Aidarkhanov). ## 2.1.8 * Improve React docs (by Nahum Zsilva). ## 2.1.7 * Reduce `index`, `async` and `non-secure` size (by @polemius). ## 2.1.6 * Reduce size (by Stas Lashmanov). * Return fast mask for Node.js. ## 2.1.5 * Reduce size (by Max Graey). * Fix IE support. ## 2.1.4 * Reduce `generate` size (by Vsevolod Rodionov). * Reduce `format` and `format` size (by Victor). * Reduce `async`, `non-secure` and `non-secure/generate` size. * Speed up `format` and `async/format` (by Max Graey). * Improve development process on Windows (by Stanislav Lashmanov). ## 2.1.3 * Improve performance (by Stephen Richardson). * Reduce size (by Stephen Richardson). ## 2.1.2 * Improve docs. ## 2.1.1 * Fix React Native support (by Shawn Hwei). ## 2.1 * Improve React Native support (by Sebastian Werner). ## 2.0.4 * Improve error text for React Native (by Sebastian Werner). ## 2.0.3 * Fix freeze on string in ID length. ## 2.0.2 * Improve docs (by Sylvanus Kateile and Mark Stosberg). ## 2.0.1 * Reduce npm package size. * Mark package as not having side effects (by @xiaody). ## 2.0 * Use `-` instead of `~` in default alphabet to by file name safe. * Add `nanoid/non-secure/generate`. ## 1.3.4 * Reduce `non-secure` size. * Add `async` callback type check. ## 1.3.3 * Fix `nanoid/async` performance regression. * Fix old Node.js `not seeded` issue in synchronous version too. ## 1.3.2 * Fix random generator `not seeded` issue of old Node.js. ## 1.3.1 * Reduce library size. ## 1.3 * Add `nanoid/async/format` and `nanoid/async/generate`. * Improve synchronous API performance. * Reduce `url` size (by Daniil Poroshin). * Improve React Native docs (by joelgetaction). ## 1.2.6 * Reduce library size (by rqrqrqrq). ## 1.2.5 * Fix Node.js 6.11.1 support (by Andrey Belym). ## 1.2.4 * Speed up Node.js secure generators (by Dmitriy Tsvettsikh). ## 1.2.3 * Fix JSDoc (by Hendry Sadrak). ## 1.2.2 * Fix distribution in `nanoid/non-secure` (by Eatall). ## 1.2.1 * Fix old Node.js support. ## 1.2 * Add `nanoid/async`. * Fix `nanoid/non-secure` JSDoc. * Add Chinese documentation (by Wenliang Dai). * Speed up and reduce size of `nanoid/non-secure` (by Ori Livni). ## 1.1.1 * Improve performance and reduce size of non-secure ID generator. ## 1.1 * Add non-secure ID generator. * Suggest to use non-secure ID generator for React Native developers. * Reduce size. ## 1.0.7 * Fix documentation. ## 1.0.6 * Fix documentation. ## 1.0.5 * Reduce `nanoid/index` size (by Anton Khlynovskiy). ## 1.0.4 * Reduce npm package size. ## 1.0.3 * Reduce npm package size. ## 1.0.2 * Fix Web Workers support (by Zachary Golba). ## 1.0.1 * Reduce `nanoid/index` size (by Anton Khlynovskiy). ## 1.0 * Use 21 symbols by default (by David Klebanoff). ## 0.2.2 * Reduce `nanoid/generate` size (by Anton Khlynovskiy). * Speed up Node.js random generator. ## 0.2.1 * Fix documentation (by Piper Chester). ## 0.2 * Add `size` argument to `nanoid()`. * Improve performance by 50%. * Reduce library size by 26% (by Vsevolod Rodionov and Oleg Mokhov). ## 0.1.1 * Reduce library size by 5%. ## 0.1 * Initial release. nanoid-5.1.7/LICENSE000066400000000000000000000021071515561125500140070ustar00rootroot00000000000000The MIT License (MIT) Copyright 2017 Andrey Sitnik Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. nanoid-5.1.7/README.ar.md000066400000000000000000000463261515561125500146750ustar00rootroot00000000000000# Nano ID Nano ID logo by Anton Lovchikov
[English](./README.md) | [日本語](./README.ja.md) | [Русский](./README.ru.md) | [简体中文](./README.zh-CN.md) | [Bahasa Indonesia](./README.id-ID.md) | [한국어](./README.ko.md) | **العربية** مُولِّد مُعرِّفات فريدة صغير الحجم وآمن ومتوافق مع الروابط (URL) لجافاسكربت. > "مستوى مذهل من الكمالية التي لا معنى لها، > والتي يستحيل ألّا تحظى بالاحترام." * **صغير الحجم.** 118 بايت فقط (بعد التصغير والضغط ببروتلي). بدون أيّ اعتماديات خارجية. يتم التحكّم بالحجم عبر [Size Limit]. * **آمن.** يستخدم مُولِّد أرقام عشوائية على مستوى العتاد. يمكن استخدامه في بيئات الكلستر. * **مُعرِّفات قصيرة.** يستخدم أبجدية أكبر من UUID وهي (`A-Za-z0-9_-`). لذا تم تقليص حجم المُعرِّف من 36 إلى 21 رمزًا. * **قابل للنقل.** تم نقل Nano ID إلى أكثر من [20 لغة برمجة](./README.md#other-programming-languages).
```js import { nanoid } from 'nanoid' model.id = nanoid() //=> "V1StGXR8_Z5jdHi6B-myT" ``` --- Made at Evil Martians, product consulting for developer tools. --- [online tool]: https://gitpod.io/#https://github.com/ai/nanoid/ [with Babel]: https://developer.epages.com/blog/coding/how-to-transpile-node-modules-with-babel-and-webpack-in-a-monorepo/ [Size Limit]: https://github.com/ai/size-limit
## جدول المحتويات - [جدول المحتويات](#جدول-المحتويات) - [المقارنة مع UUID](#المقارنة-مع-uuid) - [اختبار الأداء](#اختبار-الأداء) - [الأمان](#الأمان) - [التثبيت](#التثبيت) - [ESM](#esm) - [CommonJS](#commonjs) - [JSR](#jsr) - [CDN](#cdn) - [واجهة البرمجة (API)](#واجهة-البرمجة-api) - [متزامن (Blocking)](#متزامن-blocking) - [غير آمن (Non-Secure)](#غير-آمن-non-secure) - [أبجدية أو حجم مخصّص](#أبجدية-أو-حجم-مخصّص) - [مُولِّد بايتات عشوائية مخصّص](#مُولِّد-بايتات-عشوائية-مخصّص) - [الاستخدام](#الاستخدام) - [React](#react) - [React Native](#react-native) - [PouchDB و CouchDB](#pouchdb-و-couchdb) - [سطر الأوامر (CLI)](#سطر-الأوامر-cli) - [TypeScript](#typescript) - [لغات البرمجة الأخرى](#لغات-البرمجة-الأخرى) - [الأدوات](#الأدوات) ## المقارنة مع UUID Nano ID قابل للمقارنة مع UUID v4 (المبني على العشوائية). يحتوي على عدد مماثل من البتّات العشوائية في المُعرِّف (126 في Nano ID و122 في UUID)، لذا فإنّ احتمالية التكرار متقاربة: > لكي تكون هناك فرصة واحدة من مليار لحدوث تكرار، > يجب توليد 103 تريليون مُعرِّف من النوع v4. يوجد اختلافان رئيسيان بين Nano ID و UUID v4: 1. يستخدم Nano ID أبجدية أكبر، لذا يتم ضغط عدد مماثل من البتّات العشوائية في 21 رمزًا فقط بدلاً من 36. 2. كود Nano ID أصغر بـ **4 مرات** من حزمة `uuid/v4`: 130 بايت مقابل 423. ## اختبار الأداء
```rust $ node ./test/benchmark.js crypto.randomUUID 7,619,041 ops/sec uuid v4 7,436,626 ops/sec @napi-rs/uuid 4,730,614 ops/sec uid/secure 4,729,185 ops/sec @lukeed/uuid 4,015,673 ops/sec nanoid 3,693,964 ops/sec customAlphabet 2,799,255 ops/sec nanoid for browser 380,915 ops/sec secure-random-string 362,316 ops/sec uid-safe.sync 354,234 ops/sec shortid 38,808 ops/sec Non-secure: uid 11,872,105 ops/sec nanoid/non-secure 2,226,483 ops/sec rndm 2,308,044 ops/sec ```
بيئة الاختبار: Framework 13 7840U، فيدورا 39، Node.js 21.6. ## الأمان *اقرأ مقالاً جيداً عن نظرية مُولِّدات الأرقام العشوائية: [Secure random values (in Node.js)]* * **عدم القابلية للتنبؤ.** بدلاً من استخدام `Math.random()` غير الآمن، يستخدم Nano ID وحدة `crypto` في Node.js و Web Crypto API في المتصفحات. هذه الوحدات تستخدم مُولِّد أرقام عشوائية على مستوى العتاد لا يمكن التنبؤ به. * **التوزيع المنتظم.** `random % alphabet` هو خطأ شائع عند برمجة مُولِّد مُعرِّفات. التوزيع لن يكون متساويًا؛ بعض الرموز ستظهر بتواتر أقل من غيرها. وهذا يقلّل عدد المحاولات اللازمة للكسر بالقوة الغاشمة. يستخدم Nano ID [خوارزمية أفضل] وقد تم اختباره للتحقّق من انتظام التوزيع. انتظام توزيع Nano ID * **موثّق جيداً:** جميع الحيل البرمجية في Nano ID موثّقة. اطّلع على التعليقات في [الكود المصدري]. * **الثغرات الأمنية:** للإبلاغ عن ثغرة أمنية، يُرجى استخدام [جهة اتصال Tidelift الأمنية](https://tidelift.com/security). سيقوم Tidelift بتنسيق الإصلاح والإفصاح. [Secure random values (in Node.js)]: https://gist.github.com/joepie91/7105003c3b26e65efcea63f3db82dfba [خوارزمية أفضل]: https://github.com/ai/nanoid/blob/main/index.js [الكود المصدري]: https://github.com/ai/nanoid/blob/main/index.js ## التثبيت ### ESM يعمل Nano ID 5 مع مشاريع ESM (باستخدام `import`) في الاختبارات أو سكربتات Node.js.
```bash npm install nanoid ```
### CommonJS يمكن استخدام Nano ID مع CommonJS بإحدى الطرق التالية: - يمكنك استخدام `require()` لاستيراد Nano ID. تحتاج إلى استخدام أحدث إصدار من Node.js 22.12 (يعمل مباشرة) أو Node.js 20 (مع علامة `--experimental-require-module`). - لـ Node.js 18 يمكنك استيراد Nano ID ديناميكيًا كالتالي:
```js let nanoid module.exports.createID = async () => { if (!nanoid) ({ nanoid } = await import('nanoid')) return nanoid() // => "V1StGXR8_Z5jdHi6B-myT" } ```
- يمكنك استخدام Nano ID 3.x (ما زلنا ندعمه):
```bash npm install nanoid@3 ```
### JSR [JSR](https://jsr.io) هو بديل لـ npm بحوكمة مفتوحة وتطوير نشط (على عكس npm).
```bash npx jsr add @sitnik/nanoid ```
يمكنك استخدامه في Node.js و Deno و Bun وغيرها.
```js // استبدل `nanoid` بـ `@sitnik/nanoid` في جميع الاستيرادات import { nanoid } from '@sitnik/nanoid' ```
لـ Deno ثبّته عبر `deno add jsr:@sitnik/nanoid` أو استورده من `jsr:@sitnik/nanoid`. ### CDN للتجارب السريعة، يمكنك تحميل Nano ID من CDN. لكن لا يُنصح باستخدامه في الإنتاج بسبب انخفاض أداء التحميل.
```js import { nanoid } from 'https://cdn.jsdelivr.net/npm/nanoid/nanoid.js' ```
## واجهة البرمجة (API) يمتلك Nano ID واجهتي برمجة: عادية وغير آمنة. بشكل افتراضي، يستخدم Nano ID رموزًا متوافقة مع الروابط (`A-Za-z0-9_-`) ويُنتج مُعرِّفًا مكوّنًا من 21 حرفًا (ليكون احتمال التكرار مماثلاً لـ UUID v4). ### متزامن (Blocking) الطريقة الأسهل والأكثر أمانًا لاستخدام Nano ID. في حالات نادرة قد يحجب المعالج عن العمليات الأخرى أثناء جمع الضوضاء لمُولِّد الأرقام العشوائية على مستوى العتاد.
```js import { nanoid } from 'nanoid' model.id = nanoid() //=> "V1StGXR8_Z5jdHi6B-myT" ```
إذا أردت تقليل حجم المُعرِّف (وزيادة احتمالية التكرار)، يمكنك تمرير الحجم كمعامل.
```js nanoid(10) //=> "IRFa-VaY2b" ```
لا تنسَ التحقّق من أمان حجم المُعرِّف الخاص بك عبر حاسبة [احتمالية تكرار المُعرِّف]. يمكنك أيضًا استخدام [أبجدية مخصّصة](#أبجدية-أو-حجم-مخصّص) أو [مُولِّد أرقام عشوائية مخصّص](#مُولِّد-بايتات-عشوائية-مخصّص). [احتمالية تكرار المُعرِّف]: https://zelark.github.io/nano-id-cc/ ### غير آمن (Non-Secure) بشكل افتراضي، يستخدم Nano ID توليد بايتات عشوائية على مستوى العتاد من أجل الأمان وتقليل احتمالية التكرار. إذا لم يكن الأمان مهمًا بالنسبة لك، يمكنك استخدامه في بيئات لا تتوفر فيها مُولِّدات أرقام عشوائية على مستوى العتاد.
```js import { nanoid } from 'nanoid/non-secure' const id = nanoid() //=> "Uakgb_J5m9g-0JDMbcJqLJ" ```
### أبجدية أو حجم مخصّص تُرجع `customAlphabet` دالة تتيح لك إنشاء `nanoid` بأبجديتك وحجمك الخاصّين.
```js import { customAlphabet } from 'nanoid' const nanoid = customAlphabet('1234567890abcdef', 10) model.id = nanoid() //=> "4f90d13a42" ``` ```js import { customAlphabet } from 'nanoid/non-secure' const nanoid = customAlphabet('1234567890abcdef', 10) user.id = nanoid() ```
تحقّق من أمان أبجديتك المخصّصة وحجم المُعرِّف عبر حاسبة [احتمالية تكرار المُعرِّف]. لمزيد من خيارات الأبجديات، اطّلع على [`nanoid-dictionary`]. يجب أن تحتوي الأبجدية على 256 رمزًا أو أقل. وإلا فإن أمان خوارزمية المُولِّد الداخلية غير مضمون. بالإضافة إلى تحديد حجم افتراضي، يمكنك تغيير حجم المُعرِّف عند استدعاء الدالة:
```js import { customAlphabet } from 'nanoid' const nanoid = customAlphabet('1234567890abcdef', 10) model.id = nanoid(5) //=> "f01a2" ``` [احتمالية تكرار المُعرِّف]: https://zelark.github.io/nano-id-cc/ [`nanoid-dictionary`]: https://github.com/CyberAP/nanoid-dictionary
### مُولِّد بايتات عشوائية مخصّص تتيح لك `customRandom` إنشاء `nanoid` واستبدال الأبجدية ومُولِّد البايتات العشوائية الافتراضي. في هذا المثال، يتم استخدام مُولِّد مبني على بذرة (seed):
```js import { customRandom } from 'nanoid' const rng = seedrandom(seed) const nanoid = customRandom('abcdef', 10, size => { return (new Uint8Array(size)).map(() => 256 * rng()) }) nanoid() //=> "fbaefaadeb" ```
يجب أن تقبل دالة `random` حجم المصفوفة وتُرجع مصفوفة من الأرقام العشوائية. إذا أردت استخدام نفس الرموز المتوافقة مع الروابط مع `customRandom`، يمكنك الحصول على الأبجدية الافتراضية عبر `urlAlphabet`.
```js const { customRandom, urlAlphabet } = require('nanoid') const nanoid = customRandom(urlAlphabet, 10, random) ```
ملاحظة: بين إصدارات Nano ID قد يتغيّر تسلسل استدعاء مُولِّد الأرقام العشوائية. إذا كنت تستخدم مُولِّدات مبنية على بذرة، فإننا لا نضمن نفس النتيجة. ## الاستخدام ### React لا توجد طريقة صحيحة لاستخدام Nano ID كخاصية `key` في React لأنها يجب أن تكون ثابتة بين عمليات التصيير (renders).
```jsx function Todos({todos}) { return (
    {todos.map(todo => (
  • /* لا تفعل هذا */ {todo.text}
  • ))}
) } ```
يجب عليك بدلاً من ذلك استخدام مُعرِّف ثابت من داخل عنصر القائمة.
```jsx const todoItems = todos.map((todo) =>
  • {todo.text}
  • ) ```
    في حال لم تمتلك مُعرِّفات ثابتة، يُفضّل استخدام الفهرس (index) كـ `key` بدلاً من `nanoid()`:
    ```jsx const todoItems = todos.map((text, index) =>
  • /* غير مُوصى به لكنه أفضل من nanoid(). استخدمه فقط إذا لم تكن لديك مُعرِّفات ثابتة. */ {text}
  • ) ```
    إذا كنت تحتاج فقط إلى مُعرِّفات عشوائية لربط العناصر ببعضها مثل labels وحقول الإدخال، يُنصح باستخدام [`useId`]. تمت إضافة هذا الـ hook في React 18. [`useId`]: https://reactjs.org/docs/hooks-reference.html#useid ### React Native لا يحتوي React Native على مُولِّد أرقام عشوائية مدمج. يعمل البوليفِل التالي مع React Native العادي و Expo بدءًا من الإصدار `39.x`. 1. اطّلع على توثيق [`react-native-get-random-values`] وثبّتها. 2. استوردها قبل Nano ID.
    ```js import 'react-native-get-random-values' import { nanoid } from 'nanoid' ``` [`react-native-get-random-values`]: https://github.com/LinusU/react-native-get-random-values
    ### PouchDB و CouchDB في PouchDB و CouchDB، لا يمكن أن تبدأ المُعرِّفات بشرطة سفلية `_`. يلزم إضافة بادئة لتجنّب هذه المشكلة، لأن Nano ID قد يستخدم `_` في بداية المُعرِّف بشكل افتراضي. أَعِد تعريف المُعرِّف الافتراضي بالخيار التالي:
    ```js db.put({ _id: 'id' + nanoid(), … }) ```
    ### سطر الأوامر (CLI) يمكنك الحصول على مُعرِّف فريد في الطرفية عبر تشغيل `npx nanoid`. تحتاج فقط إلى Node.js مثبّتًا على النظام. لا يلزم تثبيت Nano ID مسبقًا.
    ```sh $ npx nanoid npx: installed 1 in 0.63s LZfXLFzPPR4NNrgjlWDxn ```
    يمكن تحديد حجم المُعرِّف المُولَّد عبر خيار `--size` (أو `-s`):
    ```sh $ npx nanoid --size 10 L3til0JS4z ```
    يمكن تحديد أبجدية مخصّصة عبر خيار `--alphabet` (أو `-a`) (لاحظ أن `--size` مطلوب في هذه الحالة):
    ```sh $ npx nanoid --alphabet abc --size 15 bccbcabaabaccab ```
    ### TypeScript يتيح Nano ID تحويل النصوص المُولَّدة إلى أنواع مبهمة (opaque types) في TypeScript. مثال:
    ```ts declare const userIdBrand: unique symbol type UserId = string & { [userIdBrand]: true } // استخدم معامل النوع الصريح: mockUser(nanoid()) interface User { id: UserId name: string } const user: User = { // يتم التحويل تلقائيًا إلى UserId: id: nanoid(), name: 'Alice' } ```
    ### لغات البرمجة الأخرى تم نقل Nano ID إلى العديد من اللغات. يمكنك استخدام هذه الإصدارات للحصول على نفس مُولِّد المُعرِّفات على جانبَي العميل والخادم.
    * [C](https://github.com/lukateras/nanoid.h) * [C#](https://github.com/codeyu/nanoid-net) * [C++](https://github.com/mcmikecreations/nanoid_cpp) * [Clojure and ClojureScript](https://github.com/zelark/nano-id) * [ColdFusion/CFML](https://github.com/JamoCA/cfml-nanoid) * [Crystal](https://github.com/mamantoha/nanoid.cr) * [Dart & Flutter](https://github.com/pd4d10/nanoid-dart) * [Elixir](https://github.com/railsmechanic/nanoid) * [Gleam](https://github.com/0xca551e/glanoid) * [Go](https://github.com/matoous/go-nanoid) * [Haskell](https://github.com/MichelBoucey/NanoID) * [Haxe](https://github.com/flashultra/uuid) * [Janet](https://sr.ht/~statianzo/janet-nanoid/) * [Java](https://github.com/wosherco/jnanoid-enhanced) * [Kotlin](https://github.com/viascom/nanoid-kotlin) * [MySQL/MariaDB](https://github.com/viascom/nanoid-mysql-mariadb) * [Nim](https://github.com/icyphox/nanoid.nim) * [OCaml](https://github.com/routineco/ocaml-nanoid) * [Perl](https://github.com/tkzwtks/Nanoid-perl) * [PHP](https://github.com/hidehalo/nanoid-php) * Python [native](https://github.com/puyuan/py-nanoid) implementation with [dictionaries](https://pypi.org/project/nanoid-dictionary) and [fast](https://github.com/oliverlambson/fastnanoid) implementation (written in Rust) * Postgres [Extension](https://github.com/spa5k/uids-postgres) and [Native Function](https://github.com/viascom/nanoid-postgres) * [R](https://github.com/hrbrmstr/nanoid) (with dictionaries) * [Ruby](https://github.com/radeno/nanoid.rb) * [Rust](https://github.com/nikolay-govorov/nanoid) * [Swift](https://github.com/ShivaHuang/swift-nanoid) * [Unison](https://share.unison-lang.org/latest/namespaces/hojberg/nanoid) * [V](https://github.com/invipal/nanoid) * [Zig](https://github.com/SasLuca/zig-nanoid)
    للبيئات الأخرى، يتوفر [سطر الأوامر] لتوليد المُعرِّفات من الطرفية. [سطر الأوامر]: #سطر-الأوامر-cli ## الأدوات * [حاسبة حجم المُعرِّف] تعرض احتمالية التكرار عند تعديل أبجدية المُعرِّف أو حجمه. * [`nanoid-dictionary`] تحتوي على أبجديات شائعة لاستخدامها مع [`customAlphabet`]. * [`nanoid-good`] للتأكد من أن المُعرِّف لا يحتوي على كلمات غير لائقة. [`nanoid-dictionary`]: https://github.com/CyberAP/nanoid-dictionary [حاسبة حجم المُعرِّف]: https://zelark.github.io/nano-id-cc/ [`customAlphabet`]: #أبجدية-أو-حجم-مخصّص [`nanoid-good`]: https://github.com/y-gagar1n/nanoid-good
    nanoid-5.1.7/README.id-ID.md000066400000000000000000000343561515561125500151610ustar00rootroot00000000000000# Nano ID Logo Nano ID oleh Anton Lovchikov [English](./README.md) | [日本語](./README.ja.md) | [Русский](./README.ru.md) | [简体中文](./README.zh-CN.md) | **Bahasa Indonesia** | [한국어](./README.ko.md) | [العربية](./README.ar.md) Sebuah generator ID yang unik dalam bentuk string yang ringan, aman, serta _URL-friendly_ untuk JavaScript. > "Sebuah tingkat kesempurnaan yang luar biasa, > yang mana tidak mungkin untuk tidak dihormati." - **Ringan.** Hanya 118 bytes (diperkecil dan brotlied). Tidak ada ketergantungan (dependencies) apapun. [Size Limit](https://github.com/ai/size-limit) mengatur ukuran dari generator ini. - **Aman.** Nano ID menggunakan RNG yang terdapat pada perangkat keras. Dapat digunakan dalam lingkungan seperti klaster. - **ID yang pendek.** Nano ID menggunakan alfabet yang lebih banyak ketimbang UUID (`A-Za-z0-9_-`), karenanya ukuran ID menjadi berkurang dari 36 menjadi 21 simbol. - **Portabel.** Nano ID telah dimigrasi untuk [20 bahasa pemrograman lainnya](#bahasa-pemrograman-lainnya). ```js import { nanoid } from 'nanoid' model.id = nanoid() //=> "V1StGXR8_Z5jdHi6B-myT" ``` Mendukung penjelajah (browser) modern, IE [dengan Babel](https://developer.epages.com/blog/coding/how-to-transpile-node-modules-with-babel-and-webpack-in-a-monorepo/), Node.js, dan React Native. ---   Made at Evil Martians, product consulting for developer tools. --- ## Table of Contents - [Table of Contents](#table-of-contents) - [Perbandingan dengan UUID](#perbandingan-dengan-uuid) - [Benchmark](#benchmark) - [Keamanan](#keamanan) - [Instalasi](#instalasi) - [API](#api) - [Blocking](#blocking) - [Non-Secure](#non-secure) - [Alfabet dan Ukuran (Custom)](#alfabet-dan-ukuran-custom) - [Generasi Random Bytes (Custom)](#generasi-random-bytes-custom) - [Penggunaan](#penggunaan) - [React](#react) - [React Native](#react-native) - [PouchDB dan CouchDB](#pouchdb-dan-couchdb) - [CLI](#cli) - [TypeScript](#typescript) - [Bahasa Pemrograman Lainnya](#bahasa-pemrograman-lainnya) - [Alat](#alat) ## Perbandingan dengan UUID Nano ID dapat dibandingkan dengan UUID v4 (yang berbasis acak / _randomly generated_). Nano ID dan UUID v4 memiliki jumlah bita yang mirip pada ID yang dihasilkan (126 bita pada NanoID dan 122 bita pada UUID), karenanya ia memiliki probabilitas _collision_ (konflik / tabrakan) yang hampir serupa: > Agar timbul kemungkinan collison / duplikasi ID satu dalam satu miliar, perlu dihasilkan 103 triliun UUID v4. Ada dua buah perbedaan antara Nano ID dan UUID v4: 1. Nano ID menggunakan alfabet yang lebih lebar, karenanya jumlah bita acak dapat 'dikemas' dalam 21 simbol, bukan 36 simbol. 2. Kode sumber Nano ID **empat kali lebih kecil** ketimbang `uuid/v4`: 130 bytes dibanding 423 bytes. ## Benchmark ```rust $ node ./test/benchmark.js crypto.randomUUID 7,619,041 ops/sec uuid v4 7,436,626 ops/sec @napi-rs/uuid 4,730,614 ops/sec uid/secure 4,729,185 ops/sec @lukeed/uuid 4,015,673 ops/sec nanoid 3,693,964 ops/sec customAlphabet 2,799,255 ops/sec nanoid for browser 380,915 ops/sec secure-random-string 362,316 ops/sec uid-safe.sync 354,234 ops/sec shortid 38,808 ops/sec Non-secure: uid 11,872,105 ops/sec nanoid/non-secure 2,226,483 ops/sec rndm 2,308,044 ops/sec ``` Konfigurasi pengujian: Framework 13 7840U, Fedora 39, Node.js 21.6. ## Keamanan _Lihat artikel yang informatif tentang teori angka acak: [Nilai acak yang aman dalam Node.js (English)](https://gist.github.com/joepie91/7105003c3b26e65efcea63f3db82dfba)_. - **Ketidakpastian.** Sebagai ganti untuk penggunaan `Math.random()`, Nano ID menggunakan modul `crypto` yang ada di dalam Nodejs dan/atau Web Crypto API dalam penjelajah (_browser_). Modul-modul ini menggunakan generator acak berbasis perangkat keras yang tidak bisa diprediksi untuk mendapatkan nilai-nilai yang tidak pasti yang aman secara kriptografis. - **Keseragaman.** Pembagian dengan rumus `random % alphabet` adalah kesalahan yang seringkali dilakukan ketika merancang sebuah generator ID. Distribusi dari nilai-nilai tersebut tidak akan seimbang; dalam artian ada kesempatan untuk beberapa simbol untuk muncul dibandingkan dengan simbol yang lain. Ini memiliki dampak yang kurang baik, yakni mengurangi jumlah percobaan ketika seseorang mencoba untuk melakukan _brute-force attacks_. Nano ID menggunakan [algoritma yang lebih baik](https://github.com/ai/nanoid/blob/main/index.js) dan sudah diuji untuk keseragamannya. Nano ID uniformity - **Terdokumentasi secara baik.** Seluruh algoritma Nano ID sudah terdokumentasi. Lihat komentar di [kode sumber](https://github.com/ai/nanoid/blob/main/index.js). - **Kerentanan.** Untuk melaporkan sebuah _security vulnerability_ atau kerentanan, mohon menggunakan [Tidelift Security Contact](https://tidelift.com/security). Tidelift akan mengkoordinasikan pembetulan dan penyingkapan dari kerentanan tersebut. ## Instalasi ```bash npm install nanoid ``` Nano ID 5 hanya tersedia untuk proyek, pengujian, atau skrip ESM Node.js. Untuk CommonJS Anda memerlukan Nano ID 3.x (kami masih mendukungnya): ```bash npm install nanoid@3 ``` Apabila ingin 'coba-coba' terlebih dahulu, dapat digunakan Nano ID melalui CDN. Hal ini tidak direkomendasikan untuk digunakan pada lingkungan produksi karena performa pemuatan (_loading_) yang berkurang. ```js import { nanoid } from 'https://cdn.jsdelivr.net/npm/nanoid/nanoid.js' ``` ## API Nano ID memiliki dua API: normal dan _non-secure_. Bawaannya, Nano ID menggunakan simbol yang _URL-friendly_ (`A-Za-z0-9_-`) dan mengembalikan ID dengan 21 karakter (untuk memiliki probabilitas collision / tabrakan yang mirip dengan UUID v4). ### Blocking Penggunaan Nano ID yang aman dan yang paling mudah. Dalam kasus langka, fungsi ini dapat menghambat CPU untuk melakukan proses yang lain ketika dalam proses 'noise-collection' untuk generasi nilai acak (yang dilakukan pada perangkat keras). ```js import { nanoid } from 'nanoid' model.id = nanoid() //=> "V1StGXR8_Z5jdHi6B-myT" ``` Apabila ingin mengurangi ukuran ID (dan meningkatkan probabilitas collision), dapat dimasukkan `size` sebagai argumen dari fungsi `nanoid()`. ```js nanoid(10) //=> "IRFa-VaY2b" ``` Jangan lupa memeriksa tingkat keamanan dari ukuran ID dalam situs [ID collision probability calculator](https://zelark.github.io/nano-id-cc/). Dapat digunakan pula [custom alphabet](#custom-alphabet-or-size) atau [random generator](#custom-random-bytes-generator) yang lain. ### Non-Secure Konfigurasi bawaan Nano ID menggunakan random bytes generator yang berasal dari perangkat keras untuk keamanan dan probabilitas collision yang rendah. Apabila tidak terlalu memikirkan soal keamanan, dapat pula menggunakan non-secure generator yang lebih cepat. ```js import { nanoid } from 'nanoid/non-secure' const id = nanoid() //=> "Uakgb_J5m9g-0JDMbcJqLJ" ``` ### Alfabet dan Ukuran (Custom) `customAlphabet` digunakan untuk membuat Nano ID dengan alfabet dan ukuran ID yang sesuai dengan kebutuhan (dapat dikustomisasi). ```js import { customAlphabet } from 'nanoid' const nanoid = customAlphabet('1234567890abcdef', 10) model.id = nanoid() //=> "4f90d13a42" ``` Ketika menggunakan fungsi ini, jangan lupa untuk memeriksa keamanan alfabet dan ukuran ID dalam [ID collision probability calculator](https://zelark.github.io/nano-id-cc/). Untuk lebih banyak alfabet, dapat menggunakan [`nanoid-dictionary`](https://github.com/CyberAP/nanoid-dictionary). Alfabet harus terbentuk dari 256 simbol atau lebih kecil. Selain itu, keamanan algoritma generasi yang berada di dalam library ini tidak dijamin aman. API non-secure yang dapat dikustomisasi dengan `customAlphabet` pun tersedia disini: ```js import { customAlphabet } from 'nanoid/non-secure' const nanoid = customAlphabet('1234567890abcdef', 10) user.id = nanoid() ``` ### Generasi Random Bytes (Custom) `customRandom` digunakan untuk membuat Nano ID yang mengganti alfabet dan algoritma _random bytes generator_ yang telah diimplementasikan pada versi bawaan (dalam artian menggunakan algoritma sendiri untuk mendapatkan random bytes). Pada contoh berikut, digunakan _seed-based generator_: ```js import { customRandom } from 'nanoid' const rng = seedrandom(seed) const nanoid = customRandom('abcdef', 10, size => { return new Uint8Array(size).map(() => 256 * rng()) }) nanoid() //=> "fbaefaadeb" ``` Fungsi _callback_ pada `random` harus menerima ukuran array dan mengembalikan sebuah array dengan angka acak. Apabila ingin menggunakan alfabet bawaan NanoID pada fungsi `customRandom`, dapat menggunakan konstanta `urlAlphabet` seperti berikut: ```js const { customRandom, urlAlphabet } = require('nanoid') const nanoid = customRandom(urlAlphabet, 10, random) ``` API asinkronus dan non-secure tidak tersedia untuk fungsi `customRandom`. ## Penggunaan ### React Dalam React, tidak ada cara yang benar bila ingin menggunakan Nano ID untuk prop `key`, karena `key` tersebut harus konsisten dalam setiap proses render yang terjadi. ```jsx function Todos({ todos }) { return (
      {todos.map(todo => ( /* JANGAN DILAKUKAN! */
    • {todo.text}
    • ))}
    ) } ``` Karena hal tersebut, disarankan untuk menggunakan ID yang stabil pada setiap objek yang di-render oleh React. ```jsx const todoItems = todos.map(todo =>
  • {todo.text}
  • ) ``` Apabila tidak memiliki ID yang stabil pada setiap _item_ yang di-render pada React, lebih baik menggunakan indeks sebuah array sebagai `key` ketimbang menggunakan fungsi `nanoid()`, seperti berikut: ```jsx const todoItems = todos.map((text, index) => ( /* Tetap tidak direkomendasikan, tetapi lebih disarankan dari 'nanoid()'. Lakukan ini apabila setiap objek / item dalam list tidak ada ID yang stabil. */
  • {text}
  • )) ``` ### React Native React Native tidak memiliki _built-in random generator_. Digunakan polyfill seperti berikut yang berjalan untuk React Native dan Expo yang bermula dari versi `39.x`. 1. Periksa dokumentasi [`react-native-get-random-values`](https://github.com/LinusU/react-native-get-random-values) dan install di aplikasi. 2. Import library tersebut sebelum Nano ID. ```js import 'react-native-get-random-values' import { nanoid } from 'nanoid' ``` ### PouchDB dan CouchDB Dalam PouchDB dan CouchDB, ID tidak bisa dimulai dengan underscore `_`. Sebuah _prefix_ dibutuhkan untuk mencegah hal ini terjadi, karena Nano ID mungkin menggunakan `_` sebagai karakter pertama dari ID yang dihasilkan. ID bawaan dapat diubah dengan opsi berikut: ```js db.put({ _id: 'id' + nanoid(), … }) ``` ### CLI Nano ID dapat didapatkan dengan cara menggunakan `npx nanoid` pada Terminal. Hanya diperlukan Node.js untuk ini, dan tidak perlu mengunduh dan menginstall Nano ID dalam sistem. ```sh $ npx nanoid npx: installed 1 in 0.63s LZfXLFzPPR4NNrgjlWDxn ``` Bila ingin mengganti alfabet atau ukuran ID, dapat menggunakan [`nanoid-cli`](https://github.com/twhitbeck/nanoid-cli). ### TypeScript Nano ID memungkinkan untuk mengubah string yang dihasilkan menjadi string opak dalam TypeScript. Sebagai contoh: ```ts declare const userIdBrand: unique symbol type UserId = string & { [userIdBrand]: true } // Gunakan parameter tipe secara eksplisit: mockUser(nanoid()) interface User { id: UserId name: string } const user: User = { // Secara otomatis diubah menjadi UserId: id: nanoid(), name: 'Alice' } ``` ### Bahasa Pemrograman Lainnya Nano ID telah bermigrasi ke berbagai macam bahasa. Seluruh versi dapat digunakan untuk mendapatkan ID generator yang sama pada sisi klien dan sisi penyedia layanan (_client-side_ dan _server-side_). - [C#](https://github.com/codeyu/nanoid-net) - [C++](https://github.com/mcmikecreations/nanoid_cpp) - [Clojure and ClojureScript](https://github.com/zelark/nano-id) - [ColdFusion/CFML](https://github.com/JamoCA/cfml-nanoid) - [Crystal](https://github.com/mamantoha/nanoid.cr) - [Dart & Flutter](https://github.com/pd4d10/nanoid-dart) - [Deno](https://github.com/ianfabs/nanoid) - [Elixir](https://github.com/railsmechanic/nanoid) - [Gleam](https://github.com/0xca551e/glanoid) - [Go](https://github.com/jaevor/go-nanoid) - [Haskell](https://github.com/MichelBoucey/NanoID) - [Haxe](https://github.com/flashultra/uuid) - [Janet](https://sr.ht/~statianzo/janet-nanoid/) - [Java](https://github.com/wosherco/jnanoid-enhanced) - [Kotlin](https://github.com/viascom/nanoid-kotlin) - [MySQL/MariaDB](https://github.com/viascom/nanoid-mysql-mariadb) - [Nim](https://github.com/icyphox/nanoid.nim) - [OCaml](https://github.com/routineco/ocaml-nanoid) - [Perl](https://github.com/tkzwtks/Nanoid-perl) - [PHP](https://github.com/hidehalo/nanoid-php) - [Python](https://github.com/puyuan/py-nanoid) with [dictionaries](https://pypi.org/project/nanoid-dictionary) - [Postgres Extension](https://github.com/spa5k/uids-postgres) - [Postgres Native Function](https://github.com/viascom/nanoid-postgres) - [R](https://github.com/hrbrmstr/nanoid) (with dictionaries) - [Ruby](https://github.com/radeno/nanoid.rb) - [Rust](https://github.com/nikolay-govorov/nanoid) - [Swift](https://github.com/ShivaHuang/swift-nanoid) - [Unison](https://share.unison-lang.org/latest/namespaces/hojberg/nanoid) - [V](https://github.com/invipal/nanoid) - [Zig](https://github.com/SasLuca/zig-nanoid) Untuk environment lainnya, [CLI](#cli) tersedia untuk melakukan generasi ID dari command line / Terminal. ## Alat - [ID Size Calculator](https://zelark.github.io/nano-id-cc/) menunjukkan probabilitas collision ketika melakukan konfigurasi alfabet dan ukuran. - [`nanoid-dictionary`](https://github.com/CyberAP/nanoid-dictionary) untuk menggunakan alfabet popular dalam fungsi [`customAlphabet`](#custom-alphabet-or-size) - [`nanoid-good`](https://github.com/y-gagar1n/nanoid-good) untuk meyakinkan bahwa ID yang di-generasi tidak memiliki kata-kata yang kurang baik (kasar, tidak sopan, dsb.). nanoid-5.1.7/README.ja.md000066400000000000000000000420651515561125500146610ustar00rootroot00000000000000# Nano ID Nano ID logo by Anton Lovchikov [English](./README.md) | **日本語** | [Русский](./README.ru.md) | [简体中文](./README.zh-CN.md) | [Bahasa Indonesia](./README.id-ID.md) | [한국어](./README.ko.md) | [العربية](./README.ar.md) JavaScriptのための小さく、安全で、URL友好的なユニークな文字列ID生成器。 > 「意味不明なレベルの完璧主義、 > これは尊敬せざるを得ない。」 * **小さい。** 118バイト(圧縮・brotli圧縮後)。依存関係なし。 [Size Limit]がサイズを管理。 * **安全。** ハードウェア乱数生成器を使用。クラスタでも利用可能。 * **短いID。** UUIDより大きなアルファベット(A-Za-z0-9_-)を使用。 そのためID長は36から21文字に短縮されています。 * **移植性。** Nano IDは[20以上のプログラミング言語](./README.md#other-programming-languages)に移植されています。 ```js import { nanoid } from 'nanoid' model.id = nanoid() //=> "V1StGXR8_Z5jdHi6B-myT" ``` --- Made at Evil Martians, product consulting for developer tools. --- [online tool]: https://gitpod.io/#https://github.com/ai/nanoid/ [with Babel]: https://developer.epages.com/blog/coding/how-to-transpile-node-modules-with-babel-and-webpack-in-a-monorepo/ [Size Limit]: https://github.com/ai/size-limit ## 目次 - [目次](#目次) - [UUIDとの比較](#uuidとの比較) - [ベンチマーク](#ベンチマーク) - [セキュリティ](#セキュリティ) - [インストール](#インストール) - [ESM](#esm) - [CommonJS](#commonjs) - [JSR](#jsr) - [CDN](#cdn) - [API](#api) - [ブロッキング](#ブロッキング) - [非セキュア](#非セキュア) - [カスタムアルファベットまたはサイズ](#カスタムアルファベットまたはサイズ) - [カスタムランダムバイト生成器](#カスタムランダムバイト生成器) - [使用方法](#使用方法) - [React](#react) - [React Native](#react-native) - [PouchDBとCouchDB](#pouchdbとcouchdb) - [CLI](#cli) - [TypeScript](#typescript) - [その他のプログラミング言語](#その他のプログラミング言語) - [ツール](#ツール) ## UUIDとの比較 Nano IDはUUID v4(ランダムベース)と十分に比較可能です。 ID内のランダムビット数は同様です(Nano IDで126ビット、UUIDで122ビット)、 そのため衝突確率も同様です: > 10億分の1の確率で重複が発生するには、 > 103兆個のバージョン4 IDを生成する必要があります。 Nano IDとUUID v4の主な違いは2つあります: 1. Nano IDはより大きなアルファベットを使用するため、同様のランダムビット数が 36文字ではなく21文字に詰め込まれています。 2. Nano IDのコードはuuid/v4パッケージより**4倍小さい**です: 423バイトではなく130バイトです。 ## ベンチマーク ```rust $ node ./test/benchmark.js crypto.randomUUID 7,619,041 ops/sec uuid v4 7,436,626 ops/sec @napi-rs/uuid 4,730,614 ops/sec uid/secure 4,729,185 ops/sec @lukeed/uuid 4,015,673 ops/sec nanoid 3,693,964 ops/sec customAlphabet 2,799,255 ops/sec nanoid for browser 380,915 ops/sec secure-random-string 362,316 ops/sec uid-safe.sync 354,234 ops/sec shortid 38,808 ops/sec Non-secure: uid 11,872,105 ops/sec nanoid/non-secure 2,226,483 ops/sec rndm 2,308,044 ops/sec ``` テスト構成:Framework 13 7840U, Fedora 39, Node.js 21.6. ## セキュリティ *乱数生成器の理論に関する良い記事を参照してください: [Secure random values (in Node.js)]* * **予測不可能性。** 安全でないMath.random()を使う代わりに、Nano IDは Node.jsではcryptoモジュールを、ブラウザではWeb Crypto APIを使用します。 これらのモジュールは予測不可能なハードウェア乱数生成器を使用します。 * **均一性。** random % alphabetはID生成器をコーディングする際によくある間違いです。 分布は均一ではなく、一部の記号が他のものより出現確率が低くなります。 そのため、総当たり攻撃の際に試行回数が減少します。Nano IDは[より良いアルゴリズム]を 使用し、均一性についてテストされています。 Nano ID uniformity * **十分に文書化されている:** Nano IDのすべてのハックは文書化されています。 [ソース]のコメントを参照してください。 * **脆弱性:** セキュリティの脆弱性を報告するには、 [Tideliftセキュリティ連絡先](https://tidelift.com/security)を使用してください。 Tideliftが修正と開示を調整します。 [Secure random values (in Node.js)]: https://gist.github.com/joepie91/7105003c3b26e65efcea63f3db82dfba [より良いアルゴリズム]: https://github.com/ai/nanoid/blob/main/index.js [ソース]: https://github.com/ai/nanoid/blob/main/index.js ## インストール ### ESM Nano ID 5はESMプロジェクト(importを使用)のテストやNode.jsスクリプトで動作します。 ```bash npm install nanoid ``` ### CommonJS Nano IDは以下のいずれかの方法でCommonJSで使用できます: - require()を使用してNano IDをインポートできます。最新のNode.js 22.12 (標準で動作)またはNode.js 20(--experimental-require-moduleオプション付き)が必要です。 - Node.js 18では、次のようにNano IDを動的にインポートできます: ```js let nanoid module.exports.createID = async () => { if (!nanoid) ({ nanoid } = await import('nanoid')) return nanoid() // => "V1StGXR8_Z5jdHi6B-myT" } ``` - Nano ID 3.xを使用できます(まだサポートしています): ```bash npm install nanoid@3 ``` ### JSR [JSR](https://jsr.io)はオープンなガバナンスと積極的な開発(npmとは対照的に)を持つnpmの代替です。 ```bash npx jsr add @sitnik/nanoid ``` Node.js、Deno、Bunなどで使用できます。 ```js // すべてのインポートで`nanoid`を`@sitnik/nanoid`に置き換える import { nanoid } from '@sitnik/nanoid' ``` Denoでは、`deno add jsr:@sitnik/nanoid`でインストールするか、 `jsr:@sitnik/nanoid`からインポートします。 ### CDN クイックハックの場合、CDNからNano IDを読み込むことができます。ただし、読み込みパフォーマンスが低いため、本番環境での使用はお勧めしません。 ```js import { nanoid } from 'https://cdn.jsdelivr.net/npm/nanoid/nanoid.js' ``` ## API Nano IDには2つのAPI:通常と非セキュアがあります。 デフォルトでは、Nano IDはURL友好的な記号(A-Za-z0-9_-)を使用し、 21文字のID(UUID v4と同様の衝突確率を持つ)を返します。 ### ブロッキング Nano IDを使用する安全で最も簡単な方法です。 まれに、ハードウェア乱数生成器のノイズ収集中にCPUを他の作業からブロックする場合があります。 ```js import { nanoid } from 'nanoid' model.id = nanoid() //=> "V1StGXR8_Z5jdHi6B-myT" ``` IDのサイズを小さくしたい場合(衝突確率を高める)、 サイズを引数として渡すことができます。 ```js nanoid(10) //=> "IRFa-VaY2b" ``` IDサイズの安全性を[ID衝突確率]計算機で確認することを忘れないでください。 [カスタムアルファベット](#カスタムアルファベットまたはサイズ)や [ランダム生成器](#カスタムランダムバイト生成器)も使用できます。 [ID衝突確率]: https://zelark.github.io/nano-id-cc/ ### 非セキュア デフォルトでは、Nano IDはセキュリティと低衝突確率のためにハードウェアランダムバイト生成を使用します。セキュリティにそれほど関心がない場合は、ハードウェア乱数生成器がない環境でも使用できます。 ```js import { nanoid } from 'nanoid/non-secure' const id = nanoid() //=> "Uakgb_J5m9g-0JDMbcJqLJ" ``` ### カスタムアルファベットまたはサイズ customAlphabetは、独自のアルファベットとIDサイズでnanoidを作成できる関数を返します。 ```js import { customAlphabet } from 'nanoid' const nanoid = customAlphabet('1234567890abcdef', 10) model.id = nanoid() //=> "4f90d13a42" ``` ```js import { customAlphabet } from 'nanoid/non-secure' const nanoid = customAlphabet('1234567890abcdef', 10) user.id = nanoid() ``` カスタムアルファベットとIDサイズの安全性を[ID衝突確率]計算機で確認してください。 より多くのアルファベットについては、[nanoid-dictionary]のオプションを確認してください。 アルファベットは256記号以下でなければなりません。 そうでない場合、内部生成アルゴリズムのセキュリティは保証されません。 デフォルトサイズを設定するだけでなく、関数を呼び出す際にIDサイズを変更することもできます: ```js import { customAlphabet } from 'nanoid' const nanoid = customAlphabet('1234567890abcdef', 10) model.id = nanoid(5) //=> "f01a2" ``` [ID衝突確率]: https://zelark.github.io/nano-id-cc/ [nanoid-dictionary]: https://github.com/CyberAP/nanoid-dictionary ### カスタムランダムバイト生成器 customRandomを使用すると、nanoidを作成し、アルファベットとデフォルトのランダムバイト生成器を置き換えることができます。 この例では、シードベースの生成器が使用されています: ```js import { customRandom } from 'nanoid' const rng = seedrandom(seed) const nanoid = customRandom('abcdef', 10, size => { return (new Uint8Array(size)).map(() => 256 * rng()) }) nanoid() //=> "fbaefaadeb" ``` randomコールバックは配列サイズを受け取り、ランダムな数値の配列を返す必要があります。 customRandomで同じURL友好的な記号を使用したい場合は、urlAlphabetを使用してデフォルトのアルファベットを取得できます。 ```js const { customRandom, urlAlphabet } = require('nanoid') const nanoid = customRandom(urlAlphabet, 10, random) ``` なお、Nano IDのバージョン間でランダム生成器の呼び出しシーケンスが変更される場合があります。シードベースの生成器を使用している場合、同じ結果を保証するものではありません。 ## 使用方法 ### React Reactの`key` propにNano IDを使用する正しい方法はありません。なぜなら、keyはレンダー間で一貫性がある必要があるからです。 ```jsx function Todos({todos}) { return (
      {todos.map(todo => (
    • /* これはやめましょう */ {todo.text}
    • ))}
    ) } ``` 代わりに、リストアイテム内で安定したIDを使用するようにしましょう。 ```jsx const todoItems = todos.map((todo) =>
  • {todo.text}
  • ) ``` 安定したIDがない場合は、`nanoid()`の代わりにインデックスを`key`として使用することをお勧めします: ```jsx const todoItems = todos.map((text, index) =>
  • /* まだ推奨されませんが、nanoid()よりは優先されます。 アイテムに安定したIDがない場合のみ行ってください。 */ {text}
  • ) ``` ラベルと入力フィールドのように要素を関連付けるためだけにランダムなIDが必要な場合は、[`useId`]が推奨されます。 このフックはReact 18で追加されました。 [`useId`]: https://reactjs.org/docs/hooks-reference.html#useid ### React Native React Nativeには組み込みのランダム生成器がありません。次のポリフィルは プレーンなReact NativeとExpo(`39.x`以降)で動作します。 1. [`react-native-get-random-values`]のドキュメントを確認し、インストールします。 2. Nano IDの前にインポートします。 ```js import 'react-native-get-random-values' import { nanoid } from 'nanoid' ``` [`react-native-get-random-values`]: https://github.com/LinusU/react-native-get-random-values ### PouchDBとCouchDB PouchDBとCouchDBでは、IDはアンダースコア`_`で始めることができません。 Nano IDはデフォルトでIDの先頭に`_`を使用する可能性があるため、 この問題を防ぐためにプレフィックスが必要です。 次のオプションでデフォルトのIDを上書きします: ```js db.put({ _id: 'id' + nanoid(), … }) ``` ### CLI ターミナルで`npx nanoid`を呼び出すことで、一意のIDを取得できます。 システムにNode.jsがあれば十分で、Nano IDをどこかにインストールする必要はありません。 ```sh $ npx nanoid npx: installed 1 in 0.63s LZfXLFzPPR4NNrgjlWDxn ``` 生成されるIDのサイズは`--size`(または`-s`)オプションで指定できます: ```sh $ npx nanoid --size 10 L3til0JS4z ``` カスタムアルファベットは`--alphabet`(または`-a`)オプションで指定できます (この場合、`--size`が必須であることに注意してください): ```sh $ npx nanoid --alphabet abc --size 15 bccbcabaabaccab ``` ### TypeScript Nano IDでは、生成された文字列をTypeScriptで不透明な文字列(opaque strings)にキャストできます。 例えば: ```ts declare const userIdBrand: unique symbol type UserId = string & { [userIdBrand]: true } // 明示的な型パラメータを使用: mockUser(nanoid()) interface User { id: UserId name: string } const user: User = { // 自動的にUserIdにキャストされます: id: nanoid(), name: 'Alice' } ``` ### その他のプログラミング言語 Nano IDは多くの言語に移植されています。これらのポートを使用して、 クライアント側とサーバー側で同じID生成器を持つことができます。 * [C](https://github.com/lukateras/nanoid.h) * [C#](https://github.com/codeyu/nanoid-net) * [C++](https://github.com/mcmikecreations/nanoid_cpp) * [Clojure and ClojureScript](https://github.com/zelark/nano-id) * [ColdFusion/CFML](https://github.com/JamoCA/cfml-nanoid) * [Crystal](https://github.com/mamantoha/nanoid.cr) * [Dart & Flutter](https://github.com/pd4d10/nanoid-dart) * [Elixir](https://github.com/railsmechanic/nanoid) * [Gleam](https://github.com/0xca551e/glanoid) * [Go](https://github.com/matoous/go-nanoid) * [Haskell](https://github.com/MichelBoucey/NanoID) * [Haxe](https://github.com/flashultra/uuid) * [Janet](https://sr.ht/~statianzo/janet-nanoid/) * [Java](https://github.com/wosherco/jnanoid-enhanced) * [Kotlin](https://github.com/viascom/nanoid-kotlin) * [MySQL/MariaDB](https://github.com/viascom/nanoid-mysql-mariadb) * [Nim](https://github.com/icyphox/nanoid.nim) * [OCaml](https://github.com/routineco/ocaml-nanoid) * [Perl](https://github.com/tkzwtks/Nanoid-perl) * [PHP](https://github.com/hidehalo/nanoid-php) * Python [ネイティブ](https://github.com/puyuan/py-nanoid)実装 [辞書](https://pypi.org/project/nanoid-dictionary)付きと [高速](https://github.com/oliverlambson/fastnanoid)実装(Rustで書かれています) * Postgres [拡張機能](https://github.com/spa5k/uids-postgres) と[ネイティブ関数](https://github.com/viascom/nanoid-postgres) * [R](https://github.com/hrbrmstr/nanoid)(辞書付き) * [Ruby](https://github.com/radeno/nanoid.rb) * [Rust](https://github.com/nikolay-govorov/nanoid) * [Swift](https://github.com/ShivaHuang/swift-nanoid) * [Unison](https://share.unison-lang.org/latest/namespaces/hojberg/nanoid) * [V](https://github.com/invipal/nanoid) * [Zig](https://github.com/SasLuca/zig-nanoid) その他の環境では、コマンドラインからIDを生成するための[CLI]が利用可能です。 [CLI]: #cli ## ツール * [IDサイズ計算機]は、IDのアルファベットやサイズを調整する際の衝突確率を表示します。 * [`nanoid-dictionary`]は[`customAlphabet`]で使用する一般的なアルファベットを提供します。 * [`nanoid-good`]はIDに不適切な単語が含まれていないことを確認します。 [`nanoid-dictionary`]: https://github.com/CyberAP/nanoid-dictionary [IDサイズ計算機]: https://zelark.github.io/nano-id-cc/ [`customAlphabet`]: #カスタムアルファベットまたはサイズ [`nanoid-good`]: https://github.com/y-gagar1n/nanoid-good nanoid-5.1.7/README.ko.md000066400000000000000000000420751515561125500147010ustar00rootroot00000000000000# Nano ID Nano ID logo by Anton Lovchikov [English](./README.md) | [日本語](./README.ja.md) | [Русский](./README.ru.md) | [简体中文](./README.zh-CN.md) | [Bahasa Indonesia](./README.id-ID.md) | **한국어** | [العربية](./README.ar.md) JavaScript를 위한 가볍고 안전하며 URL 친화적인 고유 String ID 생성기 > “대단한 레벨의 무의미한 완벽주의, > 경의를 표하지 않을 수 없습니다” * **가볍습니다.** 118 bytes (minified 및 brotli 적용 후). 다른 의존성이 없습니다. [Size Limit] 의 기능으로 컨트롤합니다. * **안전합니다.** 하드웨어의 랜덤 생성기를 사용합니다. 클러스터에서 사용할 수 있습니다. * **짧은 ID를 생성합니다.** UUID와는 다르게 대소문자를 모두 사용하여 키를 생성하므로, 36 byte를 차지하는 UUID와 다르게 21 byte만으로도 고유 아이디를 생성할 수 있습니다. So ID size was reduced from 36 to 21 symbols. * **이식이 쉽습니다.** Nano ID 는 20개 이상의 언어로 포팅되었습니다 [다른 언어들](#다른-언어들). ```js import { nanoid } from 'nanoid' model.id = nanoid() //=> "V1StGXR8_Z5jdHi6B-myT" ``` ---   Made at Evil Martians, product consulting for developer tools. --- [online tool]: https://gitpod.io/#https://github.com/ai/nanoid/ [with Babel]: https://developer.epages.com/blog/coding/how-to-transpile-node-modules-with-babel-and-webpack-in-a-monorepo/ [Size Limit]: https://github.com/ai/size-limit ## 목차 - [목차](#목차) - [UUID와 비교](#uuid와-비교) - [벤치마크](#벤치마크) - [보안](#보안) - [설치](#설치) - [ESM](#esm) - [CommonJS](#commonjs) - [JSR](#jsr) - [CDN](#cdn) - [API](#api) - [Blocking](#blocking) - [Non-Secure](#non-secure) - [사용자 커스텀 문자열](#사용자-커스텀-문자열) - [사용자 지정 랜덤 바이트 생성기](#사용자-지정-랜덤-바이트-생성기) - [사용법](#사용법) - [React](#react) - [React Native](#react-native) - [PouchDB 및 CouchDB](#pouchdb-및-couchdb) - [CLI](#cli) - [TypeScript](#typescript) - [다른 언어들](#다른-언어들) - [도구](#도구) ## UUID와 비교 Nano ID 는 (랜덤 기반의) UUID v4와 비교할 수 있습니다. 아이디로 생성되는 랜덤 비트의 수가 유사하여 (Nano ID는 126개, UUID는 122개), 동일한 아이디가 생성될 수 있는 충돌 확률도 비슷합니다: > 10억 분의 1의 확률로 충돌이 발생하기 위해서는 > 103조 번의 v4 ID가 생성되어야 합니다. Nano ID와 UUID v4에는 두 가지의 주요한 차이점이 있습니다: 1. Nano ID는 대문자를 사용합니다. 그래서 유사한 개수의 랜덤 값을 36개가 아닌 21개의 문자로 나타낼 수 있습니다. 2. Nano ID 코드는 `uuid/v4` 패키지보다 **4분의 1 사이즈**입니다: UUIDv4는 423 bytes, Nano ID는 130 bytes 입니다. ## 벤치마크 ```rust $ node ./test/benchmark.js crypto.randomUUID 7,619,041 ops/sec uuid v4 7,436,626 ops/sec @napi-rs/uuid 4,730,614 ops/sec uid/secure 4,729,185 ops/sec @lukeed/uuid 4,015,673 ops/sec nanoid 3,693,964 ops/sec customAlphabet 2,799,255 ops/sec nanoid for browser 380,915 ops/sec secure-random-string 362,316 ops/sec uid-safe.sync 354,234 ops/sec shortid 38,808 ops/sec Non-secure: uid 11,872,105 ops/sec nanoid/non-secure 2,226,483 ops/sec rndm 2,308,044 ops/sec ``` 테스트 환경: 프레임워크 13 7840U, 페도라 39, Node.js 21.6. ## 보안 *랜덤 생성기에 대한 설명은 다음 기사를 참고하세요: [Secure random values (in Node.js)]* * **예측불가성.** 안전하지 않은 `Math.random()`를 사용하는 대신, Nano ID는 Node.js에서 제공하는 `crypto` 모듈과 브라우저의 Web Crypto API를 사용합니다. 이 모듈들은 예측이 불가능한 하드웨어 레벨의 랜덤 생성기입니다. * **균일성.** `random % alphabet` 는 랜덤 아이디 생성기를 만들때 흔히들 하는 실수입니다. 이 경우 분포(수학)가 일정하지 않게 되며, 일부 기호들은 다른 기호들보다 사용될 확률이 낮아집니다. 이로 인해 브루트포스를 사용한 시도의 횟수를 줄일 수 있는 결과를 가져옵니다. Nano ID는 [이보다 더 좋은 알고리즘]을 사용하며, 균일성 테스트를 수행하였습니다. Nano ID uniformity * **문서화:** Nano ID의 모든것이 코드에 문서화되어있습니다. [소스 코드]에서 코멘트를 확인하세요. * **취약점:** 보안 취약점에 대한 리포트는 아래 링크를 사용해주세요. [Tidelift security contact](https://tidelift.com/security). Tidelift에서 취약점에 대한 수정 및 알림등을 도와줄 수 있습니다. [Secure random values (in Node.js)]: https://gist.github.com/joepie91/7105003c3b26e65efcea63f3db82dfba [이보다 더 좋은 알고리즘]: https://github.com/ai/nanoid/blob/main/index.js [소스 코드]: https://github.com/ai/nanoid/blob/main/index.js ## 설치 ### ESM Nano ID 5는 ESM 프로젝트에서 `import`를 사용하여 테스트코드나 Node.js 스크립트에 사용할 수 있습니다. ```bash npm install nanoid ``` ### CommonJS Nano ID는 아래와 같은 방법으로 CommonJS에 사용할 수 있습니다: - `require()`를 사용해 Nano ID를 가져올 수 있습니다. 최신 Node.js 22.12나 Node.js 20에서 `--experimental-require-module` 플래그를 이용하면 사용할 수 있습니다. - Node.js 18에서는 아래의 방법으로 동적 임포트를 해주세요: ```js let nanoid module.exports.createID = async () => { if (!nanoid) ({ nanoid } = await import('nanoid')) return nanoid() // => "V1StGXR8_Z5jdHi6B-myT" } ``` - Nano ID 3.x 역시 설치할 수 있습니다 (아직 지원중이에요!): ```bash npm install nanoid@3 ``` ### JSR [JSR](https://jsr.io) 은 npm을 대체할 수 있는 오픈 거버넌스이며 npm과 달리 현재 활발히 개발중에 있습니다. ```bash npx jsr add @sitnik/nanoid ``` Node.js, Deno, Bun 등에서 사용할 수 있습니다. ```js // 모든 `nanoid` import를 `@sitnik/nanoid`로 변경합니다 import { nanoid } from '@sitnik/nanoid' ``` Deno 사용시에는 `deno add jsr:@sitnik/nanoid` 명령어로 설치하고 `jsr:@sitnik/nanoid`로 import 합니다. ### CDN 빠른 적용을 위해 CDN에서 Nano ID를 가져올 수 있습니다. 하지만 로딩 성능이 늦어지므로 프로덕션에서는 사용하는 것을 추천하지 않습니다. ```js import { nanoid } from 'https://cdn.jsdelivr.net/npm/nanoid/nanoid.js' ``` ## API Nano ID는 normal / non-secure의 2가지의 API를 제공합니다. 기본적으로 Nano ID는 URL에 친화적인 기호들을 사용하여 21자리의 랜덤한 문자열을 생성합니다. (이들은 UUID v4와 유사한 중복생성 확률을 가집니다) ### Blocking Nano ID를 사용하는 가장 안전하고 쉬운 방법입니다. 드물게 CPU가 하드웨어 랜덤 생성을 위해 노이즈 제거를 수행하는 동안 다른 동작을 못하도록 블로킹 될 수 있습니다. ```js import { nanoid } from 'nanoid' model.id = nanoid() //=> "V1StGXR8_Z5jdHi6B-myT" ``` 생성되는 랜덤 아이디의 크기를 줄이고 싶으면 파라미터로 해당 길이 값을 넣어주면 됩니다. (이렇게 하면 중복 생성이 발생할 확률도 올라갑니다) ```js nanoid(10) //=> "IRFa-VaY2b" ``` 아래의 [아이디 중복확률] 계산기로 여러분의 아이디가 얼마나 안전한지 확인해보세요. [사용자 커스텀 문자열](#사용자-커스텀-문자열) 이나 [사용자가 만든 랜덤 생성기](#사용자-지정-랜덤-바이트-생성기) 를 사용할 수도 있습니다. [아이디 중복확률]: https://zelark.github.io/nano-id-cc/ ### Non-Secure 기본적으로 Nano ID는 보안과 낮은 충돌 확률을 위해 하드웨어 랜덤 바이트 생성기를 사용합니다. 만약 보안이 중요하지 않다면 하드웨어 랜덤 생성기를 사용하지 않도록 설정할 수 있습니다. ```js import { nanoid } from 'nanoid/non-secure' const id = nanoid() //=> "Uakgb_J5m9g-0JDMbcJqLJ" ``` ### 사용자 커스텀 문자열 `customAlphabet` 함수를 사용하면 지정된 문자열 내에서 지정된 개수로 이루어진 랜덤 아이디를 생성할 수 있는 `nanoid` 함수를 만들 수 있습니다 ```js import { customAlphabet } from 'nanoid' const nanoid = customAlphabet('1234567890abcdef', 10) model.id = nanoid() //=> "4f90d13a42" ``` ```js import { customAlphabet } from 'nanoid/non-secure' const nanoid = customAlphabet('1234567890abcdef', 10) user.id = nanoid() ``` [아이디 충돌 확률] 계산기를 사용하여 여러분이 지정한 문자와 사이즈에 대한 중복 생성 확률을 확인해보세요. [`nanoid-dictionary`] 에서 어떤 문자열을 사용할 수 있는지에 대한 옵션을 확인할 수 있습니다. 커스텀 문자열은 256개 이하의 개수를 가져야 합니다. 그 외의 경우 내부의 생성 알고리즘의 보안성을 보장할 수 없습니다. 기본 사이즈를 지정한 후에, 새로 만들어진 함수를 부를 때 생성할 문자열의 개수를 다시 지정하는 것도 가능합니다 ```js import { customAlphabet } from 'nanoid' const nanoid = customAlphabet('1234567890abcdef', 10) model.id = nanoid(5) //=> "f01a2" ``` [아이디 충돌 확률]: https://zelark.github.io/nano-id-cc/ [`nanoid-dictionary`]: https://github.com/CyberAP/nanoid-dictionary ### 사용자 지정 랜덤 바이트 생성기 `customRandom` 함수를 사용하면 `nanoid`에서 사용할 문자열과 알고리즘을 지정할 수 있습니다. 아래 예시는 시드 값을 기반으로 하는 랜덤 생성기를 사용하였습니다. ```js import { customRandom } from 'nanoid' const rng = seedrandom(seed) const nanoid = customRandom('abcdef', 10, size => { return (new Uint8Array(size)).map(() => 256 * rng()) }) nanoid() //=> "fbaefaadeb" ``` 콜백 함수 `random` 는 반드시 배열의 크기를 받을 수 있어야 하며, 랜덤 숫자로 이루어진 배열을 리턴해야 합니다. URL 친화적인 기호들을 사용하여 `customRandom` 을 실행하려면, `urlAlphabet`을 사용해 기본 문자셋을 가져올 수 있습니다. ```js const { customRandom, urlAlphabet } = require('nanoid') const nanoid = customRandom(urlAlphabet, 10, random) ``` 참고로, Nano ID 버전이 변경됨에 따라 랜덤 생성기의 호출 시퀀스가 변경될 수 있습니다. 시드기반 생성기를 사용하는 경우 동일한 결과가 나오는 것을 보장할 수 없습니다. ## 사용법 ### React React에서 `key` props에 Nano ID를 사용하는 것은 좋지 않습니다. 이 값은 렌더링 될 때마다 동일한 값을 가지고 있어야 합니다. ```jsx function Todos({todos}) { return (
      {todos.map(todo => (
    • /* 절대 하지 마세요 */ {todo.text}
    • ))}
    ) } ``` 랜덤값보다 리스트 내에서 가져올 수 있는 값을 사용하여 안정된 값을 키 값으로 사용하는 것이 좋습니다. ```jsx const todoItems = todos.map((todo) =>
  • {todo.text}
  • ) ``` `key` 값으로 사용할 적절한 값이 없는 경우에도 `nanoid()`를 사용하기 보다는 인덱스 값을 사용하세요: ```jsx const todoItems = todos.map((text, index) =>
  • /* 추천되는 방식은 아니지만 nanoid()를 쓰는것 보단 낫습니다 */ {text}
  • ) ``` 랜덤한 아이디를 생성하여 HTML 요소간의 연결 (label과 input 등)에 사용하는 경우에는 React 18에서 추가된 [`useId`] 를 추천합니다. [`useId`]: https://reactjs.org/docs/hooks-reference.html#useid ### React Native React Native에는 내장된 랜덤 생성기가 존재하지 않습니다. 아래의 폴리필을 사용하면 순수 React Native와 Expo(`39`버전 이상) 환경에서 Nano ID를 사용할 수 있습니다. 1. [`react-native-get-random-values`] 문서를 확인하고 설치합니다 2. Nano ID를 import하기 전에 이 패키지를 import 해야 합니다. ```js import 'react-native-get-random-values' import { nanoid } from 'nanoid' ``` [`react-native-get-random-values`]: https://github.com/LinusU/react-native-get-random-values ### PouchDB 및 CouchDB PouchDB와 CouchDB에서는 ID 값을 `_`로 시작할 수 없습니다. Nano ID는 기본적으로 `_`를 맨 앞에 붙일 수 있기 때문에, 이 문제를 해결하기 위해 접두어 (prefix)가 필요합니다. 아래와 같이 접두어를 붙여서 사용합니다. ```js db.put({ _id: 'id' + nanoid(), … }) ``` ### CLI 터미널에서 `npx nanoid` 명령어를 입력하면 고유 ID를 생성할 수 있습니다. Node.js가 시스템에 설치되어있어야 하며, Nano ID는 미리 설치되어있지 않아도 됩니다. ```sh $ npx nanoid npx: installed 1 in 0.63s LZfXLFzPPR4NNrgjlWDxn ``` 생성할 아이디의 길이를 변경하려면 `--size` (or `-s`) 옵션을 붙여줍니다: ```sh $ npx nanoid --size 10 L3til0JS4z ``` 사용자 커스텀 문자열을 사용하려면 `--alphabet` (or `-a`) 옵션을 사용합니다 (이 때 `--size`도 같이 사용해야 합니다): ```sh $ npx nanoid --alphabet abc --size 15 bccbcabaabaccab ``` ### TypeScript Nano ID는 생성된 문자열을 TypeScript의 순수 string이 아닌 타입에도 할당할 수 있습니다. 예를 들어 아래와 같이 가능합니다: ```ts declare const userIdBrand: unique symbol type UserId = string & { [userIdBrand]: true } // 명시적으로 타입 파라미터를 사용: mockUser(nanoid()) interface User { id: UserId name: string } const user: User = { // 자동으로 UserId 타입으로 캐스팅됨: id: nanoid(), name: 'Alice' } ``` ### 다른 언어들 Nano ID는 다양한 언어로 포팅되었습니다. 클라이언트/서버에 관계없이 아래의 다양한 포팅된 버전들을 사용할 수 있습니다. * [C](https://github.com/lukateras/nanoid.h) * [C#](https://github.com/codeyu/nanoid-net) * [C++](https://github.com/mcmikecreations/nanoid_cpp) * [Clojure and ClojureScript](https://github.com/zelark/nano-id) * [ColdFusion/CFML](https://github.com/JamoCA/cfml-nanoid) * [Crystal](https://github.com/mamantoha/nanoid.cr) * [Dart & Flutter](https://github.com/pd4d10/nanoid-dart) * [Elixir](https://github.com/railsmechanic/nanoid) * [Gleam](https://github.com/0xca551e/glanoid) * [Go](https://github.com/matoous/go-nanoid) * [Haskell](https://github.com/MichelBoucey/NanoID) * [Haxe](https://github.com/flashultra/uuid) * [Janet](https://sr.ht/~statianzo/janet-nanoid/) * [Java](https://github.com/wosherco/jnanoid-enhanced) * [Kotlin](https://github.com/viascom/nanoid-kotlin) * [MySQL/MariaDB](https://github.com/viascom/nanoid-mysql-mariadb) * [Nim](https://github.com/icyphox/nanoid.nim) * [OCaml](https://github.com/routineco/ocaml-nanoid) * [Perl](https://github.com/tkzwtks/Nanoid-perl) * [PHP](https://github.com/hidehalo/nanoid-php) * Python [native](https://github.com/puyuan/py-nanoid) implementation with [dictionaries](https://pypi.org/project/nanoid-dictionary) and [fast](https://github.com/oliverlambson/fastnanoid) implementation (written in Rust) * Postgres [Extension](https://github.com/spa5k/uids-postgres) and [Native Function](https://github.com/viascom/nanoid-postgres) * [R](https://github.com/hrbrmstr/nanoid) (with dictionaries) * [Ruby](https://github.com/radeno/nanoid.rb) * [Rust](https://github.com/nikolay-govorov/nanoid) * [Swift](https://github.com/ShivaHuang/swift-nanoid) * [Unison](https://share.unison-lang.org/latest/namespaces/hojberg/nanoid) * [V](https://github.com/invipal/nanoid) * [Zig](https://github.com/SasLuca/zig-nanoid) 이 외의 환경에서는 [CLI]를 사용하여 터미널 환경에서 랜덤 아이디를 생성할 수 있습니다. [CLI]: #cli ## 도구 * [ID 사이즈 계산기]는 문자열과 생성 사이즈를 변경한 경우 중복된 아이디가 생성될 수 있는 충돌 확률을 알려줍니다. * [`customAlphabet`]에서 사용할 수 있는 일반적인 문자열들을 [`nanoid-dictionary`]로 찾아볼 수 있습니다. * 생성된 ID에 이상한 단어가 들어가는 것을 방지하려면 [`nanoid-good`]를 사용할 수 있습니다. [`nanoid-dictionary`]: https://github.com/CyberAP/nanoid-dictionary [ID 사이즈 계산기]: https://zelark.github.io/nano-id-cc/ [`customAlphabet`]: #custom-alphabet-or-size [`nanoid-good`]: https://github.com/y-gagar1n/nanoid-good nanoid-5.1.7/README.md000066400000000000000000000345271515561125500142740ustar00rootroot00000000000000# Nano ID Nano ID logo by Anton Lovchikov **English** | [日本語](./README.ja.md) | [Русский](./README.ru.md) | [简体中文](./README.zh-CN.md) | [Bahasa Indonesia](./README.id-ID.md) | [한국어](./README.ko.md) | [العربية](./README.ar.md) A tiny, secure, URL-friendly, unique string ID generator for JavaScript. > “An amazing level of senseless perfectionism, > which is simply impossible not to respect.” * **Small.** 118 bytes (minified and brotlied). No dependencies. [Size Limit] controls the size. * **Safe.** It uses hardware random generator. Can be used in clusters. * **Short IDs.** It uses a larger alphabet than UUID (`A-Za-z0-9_-`). So ID size was reduced from 36 to 21 symbols. * **Portable.** Nano ID was ported to over [20 programming languages](./README.md#other-programming-languages). ```js import { nanoid } from 'nanoid' model.id = nanoid() //=> "V1StGXR8_Z5jdHi6B-myT" ``` ---   Made at Evil Martians, product consulting for developer tools. --- [online tool]: https://gitpod.io/#https://github.com/ai/nanoid/ [with Babel]: https://developer.epages.com/blog/coding/how-to-transpile-node-modules-with-babel-and-webpack-in-a-monorepo/ [Size Limit]: https://github.com/ai/size-limit ## Table of Contents - [Table of Contents](#table-of-contents) - [Comparison with UUID](#comparison-with-uuid) - [Benchmark](#benchmark) - [Security](#security) - [Install](#install) - [ESM](#esm) - [CommonJS](#commonjs) - [JSR](#jsr) - [CDN](#cdn) - [API](#api) - [Blocking](#blocking) - [Non-Secure](#non-secure) - [Custom Alphabet or Size](#custom-alphabet-or-size) - [Custom Random Bytes Generator](#custom-random-bytes-generator) - [Usage](#usage) - [React](#react) - [React Native](#react-native) - [PouchDB and CouchDB](#pouchdb-and-couchdb) - [CLI](#cli) - [TypeScript](#typescript) - [Other Programming Languages](#other-programming-languages) - [Tools](#tools) ## Comparison with UUID Nano ID is quite comparable to UUID v4 (random-based). It has a similar number of random bits in the ID (126 in Nano ID and 122 in UUID), so it has a similar collision probability: > For there to be a one in a billion chance of duplication, > 103 trillion version 4 IDs must be generated. There are two main differences between Nano ID and UUID v4: 1. Nano ID uses a bigger alphabet, so a similar number of random bits are packed in just 21 symbols instead of 36. 2. Nano ID code is **4 times smaller** than `uuid/v4` package: 118 bytes instead of 423. ## Benchmark ```rust $ node ./test/benchmark.js crypto.randomUUID 7,619,041 ops/sec uuid v4 7,436,626 ops/sec @napi-rs/uuid 4,730,614 ops/sec uid/secure 4,729,185 ops/sec @lukeed/uuid 4,015,673 ops/sec nanoid 3,693,964 ops/sec customAlphabet 2,799,255 ops/sec nanoid for browser 380,915 ops/sec secure-random-string 362,316 ops/sec uid-safe.sync 354,234 ops/sec shortid 38,808 ops/sec Non-secure: uid 11,872,105 ops/sec nanoid/non-secure 2,226,483 ops/sec rndm 2,308,044 ops/sec ``` Test configuration: Framework 13 7840U, Fedora 39, Node.js 21.6. ## Security *See a good article about random generators theory: [Secure random values (in Node.js)]* * **Unpredictability.** Instead of using the unsafe `Math.random()`, Nano ID uses the `crypto` module in Node.js and the Web Crypto API in browsers. These modules use unpredictable hardware random generator. * **Uniformity.** `random % alphabet` is a popular mistake to make when coding an ID generator. The distribution will not be even; there will be a lower chance for some symbols to appear compared to others. So, it will reduce the number of tries when brute-forcing. Nano ID uses a [better algorithm] and is tested for uniformity. Nano ID uniformity * **Well-documented:** all Nano ID hacks are documented. See comments in [the source]. * **Vulnerabilities:** to report a security vulnerability, please use the [Tidelift security contact](https://tidelift.com/security). Tidelift will coordinate the fix and disclosure. [Secure random values (in Node.js)]: https://gist.github.com/joepie91/7105003c3b26e65efcea63f3db82dfba [better algorithm]: https://github.com/ai/nanoid/blob/main/index.js [the source]: https://github.com/ai/nanoid/blob/main/index.js ## Install ### ESM Nano ID 5 works with ESM projects (with `import`) in tests or Node.js scripts. ```bash npm install nanoid ``` ### CommonJS Nano ID can be used with CommonJS in one of the following ways: - You can use `require()` to import Nano ID. You need to use latest Node.js 22.12 (works out-of-the-box) or Node.js 20 (with `--experimental-require-module`). - For Node.js 18 you can dynamically import Nano ID as follows: ```js let nanoid module.exports.createID = async () => { if (!nanoid) ({ nanoid } = await import('nanoid')) return nanoid() // => "V1StGXR8_Z5jdHi6B-myT" } ``` - You can use Nano ID 3.x (we still support it): ```bash npm install nanoid@3 ``` ### JSR [JSR](https://jsr.io) is a replacement for npm with open governance and active development (in contrast to npm). ```bash npx jsr add @sitnik/nanoid ``` You can use it in Node.js, Deno, Bun, etc. ```js // Replace `nanoid` to `@sitnik/nanoid` in all imports import { nanoid } from '@sitnik/nanoid' ``` For Deno install it by `deno add jsr:@sitnik/nanoid` or import from `jsr:@sitnik/nanoid`. ### CDN For quick hacks, you can load Nano ID from CDN. Though, it is not recommended to be used in production because of the lower loading performance. ```js import { nanoid } from 'https://cdn.jsdelivr.net/npm/nanoid/nanoid.js' ``` ## API Nano ID has 2 APIs: normal and non-secure. By default, Nano ID uses URL-friendly symbols (`A-Za-z0-9_-`) and returns an ID with 21 characters (to have a collision probability similar to UUID v4). ### Blocking The safe and easiest way to use Nano ID. In rare cases could block CPU from other work while noise collection for hardware random generator. ```js import { nanoid } from 'nanoid' model.id = nanoid() //=> "V1StGXR8_Z5jdHi6B-myT" ``` If you want to reduce the ID size (and increase collisions probability), you can pass the size as an argument. ```js nanoid(10) //=> "IRFa-VaY2b" ``` Don’t forget to check the safety of your ID size in our [ID collision probability] calculator. You can also use a [custom alphabet](#custom-alphabet-or-size) or a [random generator](#custom-random-bytes-generator). [ID collision probability]: https://zelark.github.io/nano-id-cc/ ### Non-Secure By default, Nano ID uses hardware random bytes generation for security and low collision probability. If you are not so concerned with security, you can use it for environments without hardware random generators. ```js import { nanoid } from 'nanoid/non-secure' const id = nanoid() //=> "Uakgb_J5m9g-0JDMbcJqLJ" ``` ### Custom Alphabet or Size `customAlphabet` returns a function that allows you to create `nanoid` with your own alphabet and ID size. ```js import { customAlphabet } from 'nanoid' const nanoid = customAlphabet('1234567890abcdef', 10) model.id = nanoid() //=> "4f90d13a42" ``` ```js import { customAlphabet } from 'nanoid/non-secure' const nanoid = customAlphabet('1234567890abcdef', 10) user.id = nanoid() ``` Check the safety of your custom alphabet and ID size in our [ID collision probability] calculator. For more alphabets, check out the options in [`nanoid-dictionary`]. Alphabet must contain 256 symbols or less. Otherwise, the security of the internal generator algorithm is not guaranteed. In addition to setting a default size, you can change the ID size when calling the function: ```js import { customAlphabet } from 'nanoid' const nanoid = customAlphabet('1234567890abcdef', 10) model.id = nanoid(5) //=> "f01a2" ``` [`nanoid-dictionary`]: https://github.com/CyberAP/nanoid-dictionary ### Custom Random Bytes Generator `customRandom` allows you to create a `nanoid` and replace alphabet and the default random bytes generator. In this example, a seed-based generator is used: ```js import { customRandom } from 'nanoid' const rng = seedrandom(seed) const nanoid = customRandom('abcdef', 10, size => { return (new Uint8Array(size)).map(() => 256 * rng()) }) nanoid() //=> "fbaefaadeb" ``` `random` callback must accept the array size and return an array with random numbers. If you want to use the same URL-friendly symbols with `customRandom`, you can get the default alphabet using the `urlAlphabet`. ```js import { customRandom, urlAlphabet } from 'nanoid' const nanoid = customRandom(urlAlphabet, 10, random) ``` Note, that between Nano ID versions we may change random generator call sequence. If you are using seed-based generators, we do not guarantee the same result. ## Usage ### React There’s no correct way to use Nano ID for React `key` prop since it should be consistent among renders. ```jsx function Todos({todos}) { return (
      {todos.map(todo => (
    • /* DON’T DO IT */ {todo.text}
    • ))}
    ) } ``` You should rather try to reach for stable ID inside your list item. ```jsx const todoItems = todos.map((todo) =>
  • {todo.text}
  • ) ``` In case you don’t have stable IDs you'd rather use index as `key` instead of `nanoid()`: ```jsx const todoItems = todos.map((text, index) =>
  • /* Still not recommended but preferred over nanoid(). Only do this if items have no stable IDs. */ {text}
  • ) ``` In case you just need random IDs to link elements like labels and input fields together, [`useId`] is recommended. That hook was added in React 18. [`useId`]: https://react.dev/reference/react/useId ### React Native React Native does not have built-in random generator. The following polyfill works for plain React Native and Expo starting with `39.x`. 1. Check [`react-native-get-random-values`] docs and install it. 2. Import it before Nano ID. ```js import 'react-native-get-random-values' import { nanoid } from 'nanoid' ``` [`react-native-get-random-values`]: https://github.com/LinusU/react-native-get-random-values ### PouchDB and CouchDB In PouchDB and CouchDB, IDs can’t start with an underscore `_`. A prefix is required to prevent this issue, as Nano ID might use a `_` at the start of the ID by default. Override the default ID with the following option: ```js db.put({ _id: 'id' + nanoid(), … }) ``` ### CLI You can get unique ID in terminal by calling `npx nanoid`. You need only Node.js in the system. You do not need Nano ID to be installed anywhere. ```sh $ npx nanoid npx: installed 1 in 0.63s LZfXLFzPPR4NNrgjlWDxn ``` Size of generated ID can be specified with `--size` (or `-s`) option: ```sh $ npx nanoid --size 10 L3til0JS4z ``` Custom alphabet can be specified with `--alphabet` (or `-a`) option (note that in this case `--size` is required): ```sh $ npx nanoid --alphabet abc --size 15 bccbcabaabaccab ``` ### TypeScript Nano ID allows casting generated strings into opaque strings in TypeScript. For example: ```ts declare const userIdBrand: unique symbol type UserId = string & { [userIdBrand]: true } // Use explicit type parameter: mockUser(nanoid()) interface User { id: UserId name: string } const user: User = { // Automatically casts to UserId: id: nanoid(), name: 'Alice' } ``` ### Other Programming Languages Nano ID was ported to many languages. You can use these ports to have the same ID generator on the client and server side. * [C](https://github.com/lukateras/nanoid.h) * [C#](https://github.com/codeyu/nanoid-net) * [C++](https://github.com/mcmikecreations/nanoid_cpp) * [Clojure and ClojureScript](https://github.com/zelark/nano-id) * [ColdFusion/CFML](https://github.com/JamoCA/cfml-nanoid) * [Crystal](https://github.com/mamantoha/nanoid.cr) * [Dart & Flutter](https://github.com/pd4d10/nanoid-dart) * [Elixir](https://github.com/railsmechanic/nanoid) * [Gleam](https://github.com/0xca551e/glanoid) * [Go](https://github.com/matoous/go-nanoid) * [Haskell](https://github.com/MichelBoucey/NanoID) * [Haxe](https://github.com/flashultra/uuid) * [Janet](https://sr.ht/~statianzo/janet-nanoid/) * [Java](https://github.com/wosherco/jnanoid-enhanced) * [Kotlin](https://github.com/viascom/nanoid-kotlin) * [MySQL/MariaDB](https://github.com/viascom/nanoid-mysql-mariadb) * [Nim](https://github.com/icyphox/nanoid.nim) * [OCaml](https://github.com/routineco/ocaml-nanoid) * [Perl](https://github.com/tkzwtks/Nanoid-perl) * [PHP](https://github.com/hidehalo/nanoid-php) * Python [native](https://github.com/puyuan/py-nanoid) implementation with [dictionaries](https://pypi.org/project/nanoid-dictionary) and [fast](https://github.com/oliverlambson/fastnanoid) implementation (written in Rust) * Postgres [Extension](https://github.com/spa5k/uids-postgres) and [Native Function](https://github.com/viascom/nanoid-postgres) * [R](https://github.com/hrbrmstr/nanoid) (with dictionaries) * [Ruby](https://github.com/radeno/nanoid.rb) * [Rust](https://github.com/nikolay-govorov/nanoid) * [Swift](https://github.com/ShivaHuang/swift-nanoid) * [Unison](https://share.unison-lang.org/latest/namespaces/hojberg/nanoid) * [V](https://github.com/invipal/nanoid) * [Zig](https://github.com/SasLuca/zig-nanoid) For other environments, [CLI] is available to generate IDs from a command line. [CLI]: #cli ## Tools * [ID size calculator] shows collision probability when adjusting the ID alphabet or size. * [`nanoid-dictionary`] with popular alphabets to use with [`customAlphabet`]. * [`nanoid-good`] to be sure that your ID doesn’t contain any obscene words. [`nanoid-dictionary`]: https://github.com/CyberAP/nanoid-dictionary [ID size calculator]: https://zelark.github.io/nano-id-cc/ [`customAlphabet`]: #custom-alphabet-or-size [`nanoid-good`]: https://github.com/y-gagar1n/nanoid-good nanoid-5.1.7/README.ru.md000066400000000000000000000467571515561125500147310ustar00rootroot00000000000000# Nano ID Логотип Nano ID от Антона Ловчикова [English](./README.md) | [日本語](./README.ja.md) | **Русский** | [简体中文](./README.zh-CN.md) | [Bahasa Indonesia](./README.id-ID.md) | [한국어](./README.ko.md) | [العربية](./README.ar.md) Генератор уникальных ID для JavaScript — лёгкий, безопасный, ID можно применять в URL. > «Поразительный уровень бессмысленного перфекционизма, > который просто невозможно не уважать» - **Лёгкий.** 118 байт (после минификации и Brotli). Без зависимостей. [Size Limit] следит за размером. - **Безопасный.** Использует аппаратный генератор случайных чисел. Можно использовать в кластерах машин. - **Короткие ID.** Используется больший алфавит, чем у UUID (`A-Za-z0-9_-`). Поэтому длина ID уменьшена с 36 до 21 символа. - **Работает везде.** Nano ID уже портировали на [20 языков программирования](#другие-языки-программирования). ```js import { nanoid } from 'nanoid' model.id = nanoid() //=> "V1StGXR8_Z5jdHi6B-myT" ``` Поддерживает современные браузеры, IE ([с Babel]), Node.js и React Native. [online tool]: https://gitpod.io/#https://github.com/ai/nanoid/ [с babel]: https://developer.epages.com/blog/coding/how-to-transpile-node-modules-with-babel-and-webpack-in-a-monorepo/ [size limit]: https://github.com/ai/size-limit ---   Сделано в Злых марсианах, продуктовом консалтинге для инструментов разработки. --- ## Оглавление - [Оглавление](#оглавление) - [Сравнение с UUID](#сравнение-с-uuid) - [Сравнение производительности](#сравнение-производительности) - [Безопасность](#безопасность) - [Подключение](#подключение) - [ESM](#esm) - [CommonJS](#commonjs) - [JSR](#jsr) - [CDN](#cdn) - [API](#api) - [Блокирующий](#блокирующий) - [Небезопасный](#небезопасный) - [Смена алфавита или длины](#смена-алфавита-или-длины) - [Смена генератора случайных чисел](#смена-генератора-случайных-чисел) - [Руководство](#руководство) - [React](#react) - [React Native](#react-native) - [PouchDB и CouchDB](#pouchdb-и-couchdb) - [Терминал](#терминал) - [TypeScript](#typescript) - [Другие языки программирования](#другие-языки-программирования) - [Инструменты](#инструменты) ## Сравнение с UUID Nano ID похож на UUID v4 (случайный). У них сравнимое число битов случайности в ID (126 у Nano ID против 122 у UUID), поэтому они обладают похожей вероятностью возникновения коллизий (повторной генерации ранее выданных ID): > Чтобы вероятность повтора приблизилась к 1 на миллиард, > нужно сгенерировать 103 триллиона ID. Но между ними есть 2 важных отличия: 1. Nano ID использует более широкий алфавит, и сравнимое количество битов случайности будут упакованы в более короткую строку (21 символ, против 36 у UUID). 2. Код Nano ID **в 4 раз меньше**, чем у `uuid/v4` — 130 байт против 423. ## Сравнение производительности ```rust $ node ./test/benchmark.js crypto.randomUUID 7,619,041 ops/sec uuid v4 7,436,626 ops/sec @napi-rs/uuid 4,730,614 ops/sec uid/secure 4,729,185 ops/sec @lukeed/uuid 4,015,673 ops/sec nanoid 3,693,964 ops/sec customAlphabet 2,799,255 ops/sec nanoid for browser 380,915 ops/sec secure-random-string 362,316 ops/sec uid-safe.sync 354,234 ops/sec shortid 38,808 ops/sec Non-secure: uid 11,872,105 ops/sec nanoid/non-secure 2,226,483 ops/sec rndm 2,308,044 ops/sec ``` Среда сравнения: Framework 13 7840U, Fedora 39, Node.js 21.6. ## Безопасность _См. также хорошую статью о теориях генераторов случайных чисел: [Secure random values (in Node.js)]_ - **Непредсказуемость.** Вместо предсказуемого `Math.random()`, Nano ID использует модуль `crypto` в Node.js и Web Crypto API в браузере. Эти модули дают доступ к аппаратному генератору случайных чисел. - **Равномерность.** Например, существует популярная ошибка `random % alphabet`, которую часто допускают при разработке генератора ID. Распределение вероятности для каждого символа может не быть одинаковым. Из-за неравномерности использования пространства алфавита, на перебор ID потребуется меньше времени, чем ожидается. Nano ID использует [более совершенный алгоритм], а равномерность распределения символов покрыта тестами. Распределение Nano ID - **Документация:** все хитрости Nano ID хорошо документированы — смотрите комментарии [в исходниках]. - **Уязвимости:** если вы нашли уязвимость в Nano ID, свяжитесь с [командой безопасности Tidelift](https://tidelift.com/security). Они проконтролируют исправление и проинформируют пользователей. [secure random values (in node.js)]: https://gist.github.com/joepie91/7105003c3b26e65efcea63f3db82dfba [более совершенный алгоритм]: https://github.com/ai/nanoid/blob/main/index.js [в исходниках]: https://github.com/ai/nanoid/blob/main/index.js ## Подключение ### ESM Nano ID 5 работает с ESM-проектами (`import`) в тестах или скриптах для Node.js. ```bash npm install nanoid ``` ### CommonJS На проектах с CommonJS вы можете использовать: - `require()` будет работать в последней версия Node.js 22.12 (из коробки) или Node.js 20 (с флагом `--experimental-require-module`). - В более старых версиях Node.js можно использовать динамический импорт: ```js let nanoid module.exports.createID = async () => { if (!nanoid) ({ nanoid } = await import('nanoid')) return nanoid() // => "V1StGXR8_Z5jdHi6B-myT" } ``` - Или можно просто взять Nano ID 3.x (мы его всё ещё поддерживаем): ```bash npm install nanoid@3 ``` ### JSR [JSR](https://jsr.io) это замена npm с открытым управлением и активной разработкой (в отличие от npm). ```bash npx jsr add @sitnik/nanoid ``` Вы можете использовать пакет с JSR в Node.js, Deno, Bun. ```js // Replace `nanoid` to `@sitnik/nanoid` in all imports import { nanoid } from '@sitnik/nanoid' ``` Для Deno установите через `deno add jsr:@sitnik/nanoid` или импортируйте `jsr:@sitnik/nanoid`. ### CDN Для быстрого прототипирования вы можете подключить Nano ID с CDN без установки. Не используйте этот способ на реальном сайте, так как он сильно бьёт по скорости загрузки сайта. ```js import { nanoid } from 'https://cdn.jsdelivr.net/npm/nanoid/nanoid.js' ``` ## API Nano ID разделён на два модуля: стандартный и небезопасный. По умолчанию используются символы, безопасные для URL (`A-Za-z0-9_-`). Длина ID по умолчанию — 21 символ (чтобы вероятность коллизий была соизмеримой с UUID v4). ### Блокирующий Безопасный и простой в использовании способ использования Nano ID. Из-за особенностей работы генератора случайных чисел при использовании этого способа ЦПУ может иногда простаивать без работы. ```js import { nanoid } from 'nanoid' model.id = nanoid() //=> "V1StGXR8_Z5jdHi6B-myT" ``` Функция также принимает необязательный аргумент, задающий длину ID: ```js nanoid(10) //=> "IRFa-VaY2b" ``` При изменении размера, всегда проверяйте риски в нашем [калькуляторе коллизий](https://zelark.github.io/nano-id-cc/). ### Небезопасный По умолчанию, Nano ID использует аппаратный генератор случайных чисел для получения непредсказуемых ID и минимизации риска возникновения коллизий (повторной генерации ранее выданных ID). Но если вам не требуется устойчивость к подбору ID, то вы можете перейти на небезопасный генератор — это полезно там, где нет доступа к API аппаратного генератора случайных чисел. ```js import { nanoid } from 'nanoid/non-secure' const id = nanoid() //=> "Uakgb_J5m9g-0JDMbcJqLJ" ``` Но учтите, что предсказуемость ID может быть использована для атаки на систему. ### Смена алфавита или длины Функция `customAlphabet` позволяет создать свою функцию `nanoid` с нужным вам алфавитом и длиной ID. ```js import { customAlphabet } from 'nanoid' const nanoid = customAlphabet('1234567890abcdef', 10) user.id = nanoid() //=> "4f90d13a42" ``` ```js import { customAlphabet } from 'nanoid/non-secure' const nanoid = customAlphabet('1234567890abcdef', 10) user.id = nanoid() ``` Не забудьте проверить риски коллизии вашего алфавита и длины [на нашем калькуляторе]. [`nanoid-dictionary`] содержит много популярных примеров альтернативных алфавитов. Алфавит должен содержать ≤256 символов. Иначе мы не сможем гарантировать непредсказуемость ID. Длину ID можно менять не только в `customAlphabet()`, но и при вызове генератора, который она вернёт: ```js import { customAlphabet } from 'nanoid' const nanoid = customAlphabet('1234567890abcdef', 10) model.id = nanoid(5) //=> "f01a2" ``` [на нашем калькуляторе]: https://zelark.github.io/nano-id-cc/ [`nanoid-dictionary`]: https://github.com/CyberAP/nanoid-dictionary ### Смена генератора случайных чисел Функция `customRandom` позволяет создать свою функцию `nanoid` со своими генераторами случайных чисел, алфавитом и длинной ID. Например, можно использовать генератор c seed для повторяемости тестов. ```js import { customRandom } from 'nanoid' const rng = seedrandom(seed) const nanoid = customRandom('abcdef', 10, size => { return new Uint8Array(size).map(() => 256 * rng()) }) nanoid() //=> "fbaefaadeb" ``` Функция в третьем аргументе `customRandom` должна принимать длину массива и возвращать нужный массив со случайными числами Если вы хотите заменить только генератор случайных чисел, но оставить URL-совместимый алфавит, то стандартный алфавит доступен в экспорте `urlAlphabet`. ```js const { customRandom, urlAlphabet } = require('nanoid') const nanoid = customRandom(urlAlphabet, 10, random) ``` ## Руководство ### React Не используйте Nano ID для генерации свойства `key` в JSX. При каждом рендере `key` будет разный, что плохо скажется на производительности. ```jsx function Todos({ todos }) { return (
      {todos.map(todo => (
    • /* НЕ ДЕЛАЙТЕ ТАК */ {todo.text}
    • ))}
    ) } ``` Для связи `` и `