{"id":15578310,"url":"https://github.com/ably/ably-js","last_synced_at":"2026-02-23T20:48:35.762Z","repository":{"id":5479483,"uuid":"6676523","full_name":"ably/ably-js","owner":"ably","description":"Javascript, Node, Typescript, React, React Native client library SDK for Ably realtime messaging service","archived":false,"fork":false,"pushed_at":"2026-02-16T17:00:08.000Z","size":35147,"stargazers_count":356,"open_issues_count":203,"forks_count":61,"subscribers_count":30,"default_branch":"main","last_synced_at":"2026-02-16T20:44:08.041Z","etag":null,"topics":["client-library","javascript","js","react-native","realtime","realtime-messaging","rest","sdk","ts","typescript"],"latest_commit_sha":null,"homepage":"https://ably.com/download","language":"JavaScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/ably.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","contributing":"CONTRIBUTING.md","funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":"MAINTAINERS.md","copyright":"COPYRIGHT","agents":null,"dco":null,"cla":null}},"created_at":"2012-11-13T19:41:13.000Z","updated_at":"2026-02-12T23:23:12.000Z","dependencies_parsed_at":"2024-01-22T11:33:40.885Z","dependency_job_id":"b9166ca9-7488-47c7-a2eb-5e5401e726d4","html_url":"https://github.com/ably/ably-js","commit_stats":{"total_commits":4017,"total_committers":56,"mean_commits":71.73214285714286,"dds":0.7689818272342545,"last_synced_commit":"0bd7aa5c4244563c072e1fa1b3f4a4c584459e04"},"previous_names":[],"tags_count":213,"template":false,"template_full_name":null,"purl":"pkg:github/ably/ably-js","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ably%2Fably-js","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ably%2Fably-js/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ably%2Fably-js/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ably%2Fably-js/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/ably","download_url":"https://codeload.github.com/ably/ably-js/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ably%2Fably-js/sbom","scorecard":{"id":161264,"data":{"date":"2025-08-11","repo":{"name":"github.com/ably/ably-js","commit":"bef0fff0efc5baae1a594413d2a230c05eeeeb9b"},"scorecard":{"version":"v5.2.1-40-gf6ed084d","commit":"f6ed084d17c9236477efd66e5b258b9d4cc7b389"},"score":5.1,"checks":[{"name":"Maintained","score":10,"reason":"30 commit(s) and 8 issue activity found in the last 90 days -- score normalized to 10","details":null,"documentation":{"short":"Determines if the project is \"actively maintained\".","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#maintained"}},{"name":"Code-Review","score":10,"reason":"all changesets reviewed","details":null,"documentation":{"short":"Determines if the project requires human code review before pull requests (aka merge requests) are merged.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#code-review"}},{"name":"CII-Best-Practices","score":0,"reason":"no effort to earn an OpenSSF best practices badge detected","details":null,"documentation":{"short":"Determines if the project has an OpenSSF (formerly CII) Best Practices Badge.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#cii-best-practices"}},{"name":"Packaging","score":-1,"reason":"packaging workflow not detected","details":["Warn: no GitHub/GitLab publishing workflow detected."],"documentation":{"short":"Determines if the project is published as a package that others can easily download, install, easily update, and uninstall.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#packaging"}},{"name":"Dangerous-Workflow","score":10,"reason":"no dangerous workflow patterns detected","details":null,"documentation":{"short":"Determines if the project's GitHub Action workflows avoid dangerous patterns.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#dangerous-workflow"}},{"name":"Binary-Artifacts","score":10,"reason":"no binaries found in the repo","details":null,"documentation":{"short":"Determines if the project has generated executable (binary) artifacts in the source repository.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#binary-artifacts"}},{"name":"Token-Permissions","score":0,"reason":"detected GitHub workflow tokens with excessive permissions","details":["Warn: jobLevel 'deployments' permission set to 'write': .github/workflows/bundle-report.yml:12","Warn: jobLevel 'deployments' permission set to 'write': .github/workflows/docs.yml:14","Info: jobLevel 'contents' permission set to 'read': .github/workflows/publish-cdn.yml:15","Warn: jobLevel 'deployments' permission set to 'write': .github/workflows/spec-coverage-report.yml:12","Warn: no topLevel permission defined: .github/workflows/bundle-report.yml:1","Warn: no topLevel permission defined: .github/workflows/check.yml:1","Warn: no topLevel permission defined: .github/workflows/docs.yml:1","Warn: no topLevel permission defined: .github/workflows/features.yml:1","Warn: no topLevel permission defined: .github/workflows/publish-cdn.yml:1","Warn: no topLevel permission defined: .github/workflows/react.yml:1","Warn: no topLevel permission defined: .github/workflows/spec-coverage-report.yml:1","Warn: no topLevel permission defined: .github/workflows/test-browser.yml:1","Warn: no topLevel permission defined: .github/workflows/test-node.yml:1","Warn: no topLevel permission defined: .github/workflows/test-package.yml:1"],"documentation":{"short":"Determines if the project's workflows follow the principle of least privilege.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#token-permissions"}},{"name":"License","score":10,"reason":"license file detected","details":["Info: project has a license file: LICENSE:0","Info: FSF or OSI recognized license: Apache License 2.0: LICENSE:0"],"documentation":{"short":"Determines if the project has defined a license.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#license"}},{"name":"Security-Policy","score":0,"reason":"security policy file not detected","details":["Warn: no security policy file detected","Warn: no security file to analyze","Warn: no security file to analyze","Warn: no security file to analyze"],"documentation":{"short":"Determines if the project has published a security policy.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#security-policy"}},{"name":"Pinned-Dependencies","score":4,"reason":"dependency not pinned by hash detected -- score normalized to 4","details":["Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/bundle-report.yml:15: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/bundle-report.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/bundle-report.yml:21: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/bundle-report.yml/main?enable=pin","Warn: third-party GitHubAction not pinned by hash: .github/workflows/bundle-report.yml:29: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/bundle-report.yml/main?enable=pin","Warn: third-party GitHubAction not pinned by hash: .github/workflows/bundle-report.yml:34: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/bundle-report.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/check.yml:12: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/check.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/check.yml:18: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/check.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/docs.yml:17: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/docs.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/docs.yml:20: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/docs.yml/main?enable=pin","Warn: third-party GitHubAction not pinned by hash: .github/workflows/docs.yml:31: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/docs.yml/main?enable=pin","Warn: third-party GitHubAction not pinned by hash: .github/workflows/docs.yml:38: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/docs.yml/main?enable=pin","Warn: third-party GitHubAction not pinned by hash: .github/workflows/features.yml:11: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/features.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/publish-cdn.yml:17: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/publish-cdn.yml/main?enable=pin","Warn: third-party GitHubAction not pinned by hash: .github/workflows/publish-cdn.yml:21: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/publish-cdn.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/publish-cdn.yml:27: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/publish-cdn.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/react.yml:14: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/react.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/react.yml:15: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/react.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/spec-coverage-report.yml:15: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/spec-coverage-report.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/spec-coverage-report.yml:21: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/spec-coverage-report.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/test-browser.yml:17: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/test-browser.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/test-browser.yml:25: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/test-browser.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/test-browser.yml:37: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/test-browser.yml/main?enable=pin","Warn: third-party GitHubAction not pinned by hash: .github/workflows/test-browser.yml:45: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/test-browser.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/test-node.yml:17: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/test-node.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/test-node.yml:25: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/test-node.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/test-node.yml:35: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/test-node.yml/main?enable=pin","Warn: third-party GitHubAction not pinned by hash: .github/workflows/test-node.yml:43: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/test-node.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/test-package.yml:12: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/test-package.yml/main?enable=pin","Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/test-package.yml:16: update your workflow using https://app.stepsecurity.io/secureworkflow/ably/ably-js/test-package.yml/main?enable=pin","Info:   0 out of  20 GitHub-owned GitHubAction dependencies pinned","Info:   0 out of   8 third-party GitHubAction dependencies pinned","Info:   9 out of   9 npmCommand dependencies pinned"],"documentation":{"short":"Determines if the project has declared and pinned the dependencies of its build process.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#pinned-dependencies"}},{"name":"Fuzzing","score":0,"reason":"project is not fuzzed","details":["Warn: no fuzzer integrations found"],"documentation":{"short":"Determines if the project uses fuzzing.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#fuzzing"}},{"name":"Signed-Releases","score":-1,"reason":"no releases found","details":null,"documentation":{"short":"Determines if the project cryptographically signs release artifacts.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#signed-releases"}},{"name":"Branch-Protection","score":-1,"reason":"internal error: error during branchesHandler.setup: internal error: githubv4.Query: Resource not accessible by integration","details":null,"documentation":{"short":"Determines if the default and release branches are protected with GitHub's branch protection settings.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#branch-protection"}},{"name":"SAST","score":0,"reason":"SAST tool is not run on all commits -- score normalized to 0","details":["Warn: 0 commits out of 30 are checked with a SAST tool"],"documentation":{"short":"Determines if the project uses static code analysis.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#sast"}},{"name":"Vulnerabilities","score":0,"reason":"31 existing vulnerabilities detected","details":["Warn: Project is vulnerable to: GHSA-968p-4wvh-cqc8","Warn: Project is vulnerable to: GHSA-qwcr-r2fm-qrc7","Warn: Project is vulnerable to: GHSA-v6h2-p8h4-qcjw","Warn: Project is vulnerable to: GHSA-grv7-fg5c-xmjg","Warn: Project is vulnerable to: GHSA-pxg6-pf52-xh8x","Warn: Project is vulnerable to: GHSA-3xgq-45jj-v275","Warn: Project is vulnerable to: GHSA-ghr5-ch3p-vcr6","Warn: Project is vulnerable to: GHSA-67mh-4wv8-2f99","Warn: Project is vulnerable to: GHSA-rv95-896h-c2vc","Warn: Project is vulnerable to: GHSA-qw6h-vgh9-j6wx","Warn: Project is vulnerable to: GHSA-fjxv-7rqg-78g4","Warn: Project is vulnerable to: GHSA-952p-6rrq-rcjv","Warn: Project is vulnerable to: GHSA-f8q6-p94x-37v3","Warn: Project is vulnerable to: GHSA-qrpm-p2h7-hrv2","Warn: Project is vulnerable to: GHSA-mwcw-c2x4-8c55","Warn: Project is vulnerable to: GHSA-9wv6-86v2-598j","Warn: Project is vulnerable to: GHSA-rhx6-c78j-4q9w","Warn: Project is vulnerable to: GHSA-x3m3-4wpv-5vgc","Warn: Project is vulnerable to: GHSA-gcx4-mw62-g8wm","Warn: Project is vulnerable to: GHSA-m6fv-jmcg-4jfg","Warn: Project is vulnerable to: GHSA-cm22-4g7w-348p","Warn: Project is vulnerable to: GHSA-8jhw-289h-jh2g","Warn: Project is vulnerable to: GHSA-64vr-g452-qvp3","Warn: Project is vulnerable to: GHSA-9cwx-2883-4wfx","Warn: Project is vulnerable to: GHSA-vg6x-rcgg-rjx6","Warn: Project is vulnerable to: GHSA-x574-m823-4x7w","Warn: Project is vulnerable to: GHSA-4r4m-qw57-chr8","Warn: Project is vulnerable to: GHSA-xcj6-pq6g-qj4x","Warn: Project is vulnerable to: GHSA-356w-63v5-8wf4","Warn: Project is vulnerable to: GHSA-859w-5945-r5v3","Warn: Project is vulnerable to: GHSA-4vvj-4cpr-p986"],"documentation":{"short":"Determines if the project has open, known unfixed vulnerabilities.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#vulnerabilities"}}]},"last_synced_at":"2025-08-16T13:30:35.234Z","repository_id":5479483,"created_at":"2025-08-16T13:30:35.234Z","updated_at":"2025-08-16T13:30:35.234Z"},"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":29754970,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-02-23T20:43:23.829Z","status":"ssl_error","status_checked_at":"2026-02-23T20:43:23.422Z","response_time":90,"last_error":"SSL_read: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["client-library","javascript","js","react-native","realtime","realtime-messaging","rest","sdk","ts","typescript"],"created_at":"2024-10-02T19:08:11.951Z","updated_at":"2026-02-23T20:48:35.700Z","avatar_url":"https://github.com/ably.png","language":"JavaScript","readme":"![Ably Chat Header](/images/JavaScriptSDK-github.png)\n[![npm version](https://img.shields.io/npm/v/ably.svg?style=flat)](https://img.shields.io/npm/v/ably.svg?style=flat)\n[![License](https://badgen.net/github/license/ably/ably-js)](https://github.com/ably/ably-js/blob/main/LICENSE)\n\n---\n\n# Ably Pub/Sub JavaScript SDK\n\nBuild any realtime experience using Ably’s Pub/Sub JavaScript SDK. Supported on all popular platforms and frameworks, including Node, React, and Web Workers.\n\nAbly Pub/Sub provides flexible APIs that deliver features such as pub-sub messaging, message history, presence, and push notifications. Utilizing Ably’s realtime messaging platform, applications benefit from its highly performant, reliable, and scalable infrastructure.\n\nAbly LiveObjects is also available as a Pub/Sub JavaScript SDK plugin. You can use LiveObjects to synchronize application state across your clients at scale.\n\nFind out more:\n\n- [Ably Pub/Sub docs](https://ably.com/docs/basics)\n- [Ably Pub/Sub Examples](https://ably.com/examples?product=pubsub)\n\n---\n\n## Getting started\n\nEverything you need to get started with Ably:\n\n- [Getting started with Pub/Sub in JavaScript](https://ably.com/docs/getting-started/javascript)\n- [Getting started with Pub/Sub in React](https://ably.com/docs/getting-started/react)\n- [Getting started with LiveObjects in JavaScript](https://ably.com/docs/liveobjects/quickstart)\n\n---\n\n## Supported platforms\n\nAbly aims to support a wide range of platforms and all current browser versions, including Chrome, Firefox, Safari, Microsoft Edge, and other modern browsers. If you experience any compatibility issues, open an issue in the repository or contact [Ably support](https://ably.com/support).\n\nThe following platforms are supported:\n\n| Platform    | Support                                                                                  |\n| ----------- | ---------------------------------------------------------------------------------------- |\n| JavaScript  | ES2017                                                                                   |\n| Node.js     | See `engines` in [package.json](https://github.com/ably/ably-js/blob/main/package.json). |\n| React       | \u003e=16.8.x                                                                                 |\n| TypeScript  | Type definitions are included in the package.                                            |\n| Web Workers | Browser bundle and [modular](#modular-variant) support.                                  |\n\n\u003e [!NOTE]\n\u003e Versions 1.2.x of the SDK support Internet Explorer \u003e=9 and other older browsers, as well as Node.js \u003e=8.17.\n\n\u003e [!IMPORTANT]\n\u003e SDK versions \u003c 1.2.36 will be [deprecated](https://ably.com/docs/platform/deprecate/protocol-v1) from November 1, 2025.\n\n---\n\n## Installation\n\nThe JavaScript SDK is available as an [NPM module](https://www.npmjs.com/package/ably). To get started with your project, install the package:\n\n```sh\nnpm install ably\n```\n\nYou can also source it directly in your HTML. (This url will point to the latest version of v2 of the SDK, the current major version, avoiding breaking changes per semver)\n\n```html\n\u003cscript src=\"https://cdn.ably.com/lib/ably.min-2.js\"\u003e\u003c/script\u003e\n```\n\n## Usage\n\nThe following code connects to Ably's realtime messaging service, subscribes to a channel to receive messages, and publishes a test message to that same channel.\n\n```javascript\n// Initialize Ably Realtime client\n// (for the REST client use new Ably.Rest({...}) instead)\nconst realtimeClient = new Ably.Realtime({ key: 'your-ably-api-key', clientId: 'me' });\n\n// Wait for connection to be established\nawait realtimeClient.connection.once('connected');\nconsole.log('Connected to Ably');\n\n// Get a reference to the 'test-channel' channel\nconst channel = realtimeClient.channels.get('test-channel');\n\n// Subscribe to all messages published to this channel\nawait channel.subscribe((message) =\u003e {\n  console.log(`Received message: ${message.data}`);\n});\n\n// Publish a test message to the channel\nawait channel.publish('test-event', 'hello world');\n```\n\n## Modular variant\n\nThe Pub/Sub SDK has a modular (tree-shakable) variant to build with a small bundle sizes.\n\n\u003cdetails\u003e\n\u003csummary\u003eModular variant details.\u003c/summary\u003e\n\nAimed at those who are concerned about their app's bundle size, the modular variant of the library allows you to create a client which has only the functionality that you choose. Unused functionality can then be tree-shaken by your module bundler.\n\nThe modular variant of the library provides:\n\n- A `BaseRealtime` class;\n- various plugins that add functionality to a `BaseRealtime` instance, such as `Rest`, `RealtimePresence`, etc.\n\nTo use this variant of the library, import the `BaseRealtime` class from `ably/modular`, along with the plugins that you wish to use. Then, pass these plugins to the `BaseRealtime` constructor as shown in the example below:\n\n```javascript\nimport { BaseRealtime, WebSocketTransport, FetchRequest, RealtimePresence } from 'ably/modular';\n\nconst client = new BaseRealtime({\n  key: 'YOUR_ABLY_API_KEY', // Replace with a real key from the Ably dashboard\n  plugins: {\n    WebSocketTransport,\n    FetchRequest,\n    RealtimePresence,\n  },\n});\n```\n\nYou must provide:\n\n- At least one HTTP request implementation; that is, one of `FetchRequest` or `XHRRequest`;\n- At least one realtime transport implementation; that is, one of `WebSocketTransport` or `XHRPolling`.\n\n`BaseRealtime` offers the same API as the `Realtime` class described in the rest of this `README`. This means that you can develop an application using the default variant of the SDK and switch to the modular version when you wish to optimize your bundle size.\n\nIn order to further reduce bundle size, the modular variant of the SDK performs less logging than the default variant. It only logs:\n\n- Messages that have a `logLevel` of 1 (that is, errors)\n- A small number of other network events\n\nIf you require more verbose logging, use the default variant of the SDK.\n\nFor more information view the [TypeDoc references](https://sdk.ably.com/builds/ably/ably-js/main/typedoc/modules/modular.html).\n\n\u003c/details\u003e\n\n---\n\n## Contribute\n\nRead the [CONTRIBUTING.md](./CONTRIBUTING.md) guidelines to contribute to Ably.\n\n---\n\n## Releases\n\nThe [CHANGELOG.md](/ably/ably-js/blob/main/CHANGELOG.md) contains details of the latest releases for this SDK. You can also view all Ably releases on [changelog.ably.com](https://changelog.ably.com).\n\n---\n\n## Support, feedback, and troubleshooting\n\nFor help or technical support, visit Ably's [support page](https://ably.com/support) or [GitHub Issues](https://github.com/ably/ably-js-nativescript/issues) for community-reported bugs and discussions.\n\n### Chrome extensions\n\nAbly Pub/Sub works out-of-the-box in background scripts for Chrome extensions using manifest v2. However, since manifest v3 background pages are no longer supported, you will need to run Ably Pub/Sub JavaScript SDK inside a service worker.\n\n\u003cdetails\u003e\n\u003csummary\u003eChrome extensions support details.\u003c/summary\u003e\n\nIf you are using this SDK in a service worker, note:\n\n- In versions of Chrome before 116, active WebSockets would not reset the 30s service worker idle timer, resulting in the client being closed prematurely.\n- In versions 116 and above, service workers will stay active as long as a client is connected.\n\nTo ensure compatibility, add the following to your `manifest.json`:\n\nIf you are using this SDK's realtime features, for example, WebSockets in a service worker, note:\n\n- In versions of Chrome before 116, active WebSockets would not reset the 30s service worker idle timer, resulting in the client being closed prematurely.\n- In versions 116 and above, service workers will stay active as long as a client is connected.\n\nTo ensure compatibility, add the following to your `manifest.json`:\n\n```json\n{\n  // ...\n  \"minimum_chrome_version\": \"116\"\n  // ...\n}\n```\n\n\u003c/details\u003e\n\n### \"Connection limit exceeded\" errors during development\n\nIf you're hitting a \"connection limit exceeded\" error and see rising connection counts in your Ably dashboard, it's likely due to multiple `Ably.Realtime` instances being created during development.\n\n\u003cdetails\u003e\n\u003csummary\u003e\"Connection limit exceeded\" support details.\u003c/summary\u003e\n\nEven for `use client` components, Next.js may execute them on the server during pre-rendering. This can create unintended `Ably.Realtime` connections from Node.js that remain open until you restart the development server.\n\nPrevent server-side connections using `autoConnect` and a window check:\n\n```typescript\nconst client = new Ably.Realtime({\n  key: 'your-ably-api-key',\n  autoConnect: typeof window !== 'undefined',\n});\n```\n\nCreating the client inside [React](https://github.com/ably/ably-js/blob/main/docs/react.md#Usage) components can lead to a new connection on every render. To prevent this, move the new `Ably.Realtime()` call outside of component functions.\n\nIn development environments that use Hot Module Replacement (HMR), such as React, Vite, or Next.js, saving a file can recreate the Ably.Realtime client, while previous instances remain connected. Over time, this leads to a growing number of active connections with each code edit. To fix: Move the client to a separate file (e.g., `ably-client.js`) and import it. This ensures the client is recreated only when that file changes.\n\n\u003c/details\u003e\n\n### Next.js with App Router and Turbopack\n\nIf you encounter a `Failed to compile Module not found` error or warnings related to `keyv` when using Ably Pub/Sub JavaScript SDK with [Next.js](https://nextjs.org/docs/app/api-reference/next-config-js/serverComponentsExternalPackages), add `ably` to the `serverComponentsExternalPackages` list in `next.config.js`.\n\n\u003cdetails\u003e\n\u003csummary\u003eNext.js with App Router and Turbopack support details.\u003c/summary\u003e\n\nThe following example adds `ably` to the `serverComponentsExternalPackages` list in `next.config.js`:\n\n```javascript\nconst nextConfig = {\n  // ...\n  experimental: {\n    serverComponentsExternalPackages: ['ably'],\n  },\n};\n```\n\nThe issue is coming from the fact that when using App Router specifically, dependencies used inside Server Components and Route Handlers will automatically be bundled by Next.js. This causes issues with some packages, usually the ones that have complex `require` statements, for example, requiring some packages dynamically during runtime. `keyv` is one of those packages as it uses `require` statement dynamically when requiring its adapters (see [code in repo](https://github.com/jaredwray/keyv/blob/main/packages/keyv/src/index.ts#L102)):\n\n`keyv` ends up being one of `ably-js`'s upstream dependencies for the node.js bundle, which causes the errors above when using it with Next.js App Router.\n\nUsing `serverComponentsExternalPackages` opts out from using Next.js bundling for specific packages and uses native Node.js `require` instead.\nThis is a common problem in App Router for a number of packages (for example, see next.js issue [vercel/next.js#52876](https://github.com/vercel/next.js/issues/52876)), and using `serverComponentsExternalPackages` is the recommended approach here.\n\n\u003c/details\u003e\n\n### Genral errors during development\n\nIf you encounter an error such as `connection limit exceeded` during development, it may be caused by several issues.\n\n\u003cdetails\u003e\n\u003csummary\u003eGeneral errors support details.\u003c/summary\u003e\n\n#### Server-side rendering (SSR)\n\nUse the `autoConnect` option to prevent the client from connecting when rendered on the server:\n\n```typescript\nconst client = new Ably.Realtime({ key: 'your-ably-api-key', autoConnect: typeof window !== 'undefined' });\n```\n\n#### Component re-renders\n\nAvoid creating the client inside React components. Instead, move the client instantiation outside of the component to prevent it from being recreated on every render.\n\n#### Hot module replacement (HMR)\n\nTo avoid duplicate client instances caused by hot reloads, move the new `Ably.Realtime()` call into a separate file, for example, `ably.js` and export the client from there. This ensures a single shared instance is reused during development.\n\n\u003c/details\u003e\n","funding_links":[],"categories":[],"sub_categories":[],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fably%2Fably-js","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fably%2Fably-js","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fably%2Fably-js/lists"}