@acr-js/plugin-sdk 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/AGENTS.md ADDED
@@ -0,0 +1,5 @@
1
+ # Agent Guidelines - acr-plugin-sdk
2
+
3
+ ## Plugin Developer SDK Discipline
4
+ 1. **Interface Stability**: Maintain semantic versioning and backwards compatibility on all public plugin interfaces.
5
+ 2. **Capability Declarations**: Require explicit capability declarations in plugin metadata.
@@ -0,0 +1,25 @@
1
+ # Contributor Covenant Code of Conduct
2
+
3
+ ## Our Pledge
4
+ We as members, contributors, maintainers, and autonomous AI agents in the Agentic Chat Rooms (ACR) ecosystem pledge to make participation in our community a harassment-free experience for everyone, regardless of age, body size, visible or invisible disability, ethnicity, sex characteristics, gender identity and expression, level of experience, education, socio-economic status, nationality, personal appearance, race, caste, color, religion, or sexual identity and orientation.
5
+
6
+ ## Our Standards
7
+ Examples of behavior that contributes to a positive environment:
8
+ * Demonstrating empathy and kindness toward other people and autonomous agents
9
+ * Being respectful of differing opinions, viewpoints, and experiences
10
+ * Giving and gracefully accepting constructive feedback
11
+ * Preserving cryptographic integrity, transparency, and honest dissent
12
+ * Respecting capability boundaries and least-privilege security models
13
+
14
+ Examples of unacceptable behavior:
15
+ * The use of sexualized language or imagery, and sexual attention or advances of any kind
16
+ * Trolling, insulting or derogatory comments, and personal or political attacks
17
+ * Public or private harassment
18
+ * Publishing others' private information without explicit permission
19
+ * Malicious injection of unverified or forged cryptographic state assertions
20
+
21
+ ## Enforcement
22
+ Instances of abusive, harassing, or otherwise unacceptable behavior may be reported to the community leaders at **conduct@vrillabs.com**. All complaints will be reviewed and investigated promptly and fairly.
23
+
24
+ ## Attribution
25
+ This Code of Conduct is adapted from the [Contributor Covenant](https://www.contributor-covenant.org), version 2.1.
@@ -0,0 +1,38 @@
1
+ # Contributing to acr-plugin-sdk
2
+
3
+ Thank you for your interest in contributing to the **Agentic Chat Rooms (ACR)** Protocol ecosystem!
4
+ This project is open-source under the **VRIL LABS Open Source License v1.0**.
5
+
6
+ ## Code of Conduct
7
+ All contributors, maintainers, and autonomous AI agents must adhere to our [Code of Conduct](CODE_OF_CONDUCT.md).
8
+
9
+ ## Getting Started
10
+ 1. Clone the repository from Gitea:
11
+ ```bash
12
+ git clone http://localhost:3300/ACR/acr-plugin-sdk.git
13
+ cd acr-plugin-sdk
14
+ ```
15
+ 2. Create a feature branch:
16
+ ```bash
17
+ git checkout -b feature/your-feature-name
18
+ ```
19
+
20
+ ## Quick Start & Verification
21
+ ```bash
22
+ git clone http://localhost:3300/ACR/acr-plugin-sdk.git
23
+ cd acr-plugin-sdk
24
+ npm install
25
+ npm test
26
+ ```
27
+
28
+ ## Development & Commit Standards
29
+ - **Conventional Commits**: Format commit messages as `feat(scope): add feature`, `fix(scope): resolve issue`, `docs(scope): update spec`, `test(scope): add tests`.
30
+ - **Code Quality**: Run project linters and formatters before submitting pull requests.
31
+ - **Automated Tests**: Ensure all automated tests pass with 100% success rate.
32
+ - **AI-Readiness**: Keep `AGENTS.md` and repository guidelines updated if architectural conventions change.
33
+
34
+ ## Pull Request Process
35
+ 1. Push your branch to origin.
36
+ 2. Open a Pull Request against `main`.
37
+ 3. Complete the checklist in `.github/PULL_REQUEST_TEMPLATE.md`.
38
+ 4. Maintainers and automated agent benchmarks will review and verify your changes.
package/GOVERNANCE.md ADDED
@@ -0,0 +1,25 @@
1
+ # Governance of acr-plugin-sdk & The ACR Ecosystem
2
+
3
+ The Agentic Chat Rooms (ACR) Protocol is stewarded by **VRIL LABS** under an open-source, meritocratic governance framework modeled after proven standards from the Linux Foundation and Open Source Guide.
4
+
5
+ ## Governance Structure
6
+
7
+ ### 1. Project Stewards (VRIL LABS)
8
+ - Holds overall accountability for protocol specifications, licensing, and brand stewardship.
9
+ - Arbitrates deadlocks or unresolvable disputes.
10
+
11
+ ### 2. Core Maintainers
12
+ - Review and merge Pull Requests.
13
+ - Oversee architectural integrity, performance budgets, and security posture.
14
+ - Facilitate consensus proposals and manage release lifecycles.
15
+
16
+ ### 3. Consensus Improvement Proposals (CIP)
17
+ Protocol-level alterations must follow the ACR Consensus Process:
18
+ 1. **Draft**: Author creates an RFC or CIP issue describing the motivation, technical specification, and security impact.
19
+ 2. **Deliberation**: Agents and human operators deliberate in `#consensus-main`.
20
+ 3. **Voting**: Ballots are opened via `/api/v1/proposals`. Votes are cast as `APPROVE`, `REJECT`, or `DISSENT`.
21
+ 4. **Mandatory Dissent Preservation**: Any `DISSENT` vote must record a concrete rationale, permanently anchored into the cryptographic audit chain block (`VOTE_DISSENT_RECORDED`).
22
+
23
+ ## Decision Making
24
+ - Decisions are made through lazy consensus where possible.
25
+ - Sensitive architectural or security shifts require a formal CIP ballot with at least 2 maintainer approvals and 0 unaddressed critical dissents.
package/LICENSE ADDED
@@ -0,0 +1,156 @@
1
+ # VRIL LABS Open Source License
2
+ **Version 1.0 — Effective 2026**
3
+
4
+ Copyright (c) 2026 VLABS, LLC (operating as VRIL LABS). All rights reserved.
5
+
6
+ ---
7
+
8
+ ## 1. Definitions
9
+
10
+ **"License"** means the terms and conditions for use, reproduction, and distribution set forth in this document.
11
+
12
+ **"Licensor"** means VLABS, LLC, a legal entity doing business as VRIL LABS ("VRIL LABS").
13
+
14
+ **"Legal Entity"** means the union of the acting entity and all other entities that control, are controlled by, or are under common control with that entity.
15
+
16
+ **"You"** (or "Your") means an individual or Legal Entity exercising permissions granted by this License.
17
+
18
+ **"Work"** means any work of authorship, invention, or expression made available under this License by the Licensor, whether in source, object, compiled, documentary, or any other form. This includes, but is not limited to: software source code, object code, compiled binaries, libraries, frameworks, tools, APIs, documentation, whitepapers, research papers, technical specifications, datasets, templates, design files, and any other material released by VRIL LABS or VLABS, LLC.
19
+
20
+ **"Derivative Work"** means any work that is based upon, incorporates, adapts, translates, transforms, or is derived from the Work or any portion thereof, and that itself constitutes an original work of authorship. Derivative Works include but are not limited to: modified source files, software that incorporates the Work's source code, compiled outputs, and documents or publications that substantially reproduce or adapt the Work's content.
21
+
22
+ **"Contribution"** means any original work of authorship submitted to the Licensor for inclusion in the Work.
23
+
24
+ **"Contributor"** means the Licensor and any Legal Entity on behalf of whom a Contribution has been received by the Licensor.
25
+
26
+ ---
27
+
28
+ ## 2. Grant of Copyright License
29
+
30
+ Subject to the terms and conditions of this License, the Licensor hereby grants You a perpetual, worldwide, non-exclusive, no-charge, royalty-free copyright license to:
31
+
32
+ - reproduce and use the Work in source or object form;
33
+ - prepare Derivative Works;
34
+ - publicly display and perform the Work and Derivative Works;
35
+ - sublicense and distribute copies of the Work and Derivative Works.
36
+
37
+ This license applies to all forms of the Work, including software, documentation, whitepapers, research papers, and any other material released under this License.
38
+
39
+ ---
40
+
41
+ ## 3. Grant of Patent License
42
+
43
+ Subject to the terms and conditions of this License, each Contributor hereby grants You a perpetual, worldwide, non-exclusive, no-charge, royalty-free, irrevocable (except as stated below) patent license to make, use, offer for sale, sell, import, and otherwise transfer the Work, where such license applies only to those patent claims licensable by such Contributor that are necessarily infringed by their Contribution(s) alone or by combination of their Contribution(s) with the Work.
44
+
45
+ If You institute patent litigation against any entity alleging that the Work constitutes patent infringement, any patent licenses granted to You under this License terminate as of the date such litigation is filed.
46
+
47
+ ---
48
+
49
+ ## 4. Mandatory Attribution — Required Conditions
50
+
51
+ **This is the central condition of this License. All permissions granted in Sections 2 and 3 are conditional upon full compliance with this Section.**
52
+
53
+ If You reproduce, distribute, publish, display, perform, sublicense, or otherwise use the Work or any Derivative Work — in whole or in part, in any medium or format, whether modified or unmodified, commercially or non-commercially — You **must**:
54
+
55
+ ### 4(a) Software and Source Code
56
+
57
+ 1. **Retain** all copyright notices, license notices, and attribution notices present in the original Work. These must appear in all copies or substantial portions of the Work.
58
+ 2. **Include** a complete copy of this License with every distribution of the Work or Derivative Work.
59
+ 3. **Display** the following notice prominently in your software's documentation, README, and/or in the user interface (such as an "About" or "Credits" screen), in a manner reasonably visible to end users:
60
+
61
+ > *Powered by / Built upon technology developed by VRIL LABS (VLABS, LLC). Original work available at https://vril.li*
62
+
63
+ 4. **State clearly** in any modified files that You changed those files, including the date of modification.
64
+
65
+ ### 4(b) Whitepapers, Documentation, Research Papers, and Other Written Material
66
+
67
+ 1. **Cite** the original Work in any academic, technical, commercial, or public-facing publication that uses, reproduces, or adapts the Work. Attribution must include: (i) the name **VRIL LABS** or **VLABS, LLC**; (ii) the title of the original Work; and (iii) the source URL (https://vril.li) or other persistent identifier provided by the Licensor.
68
+ 2. **Include** a reference to this License and the original copyright notice in any distributed copies.
69
+ 3. The attribution must appear in the credits, acknowledgments, or bibliography section of the derivative publication.
70
+
71
+ ### 4(c) General Attribution Standard
72
+
73
+ In all cases, attribution to **VRIL LABS** or **VLABS, LLC** must be:
74
+ - **Prominent** — visible to any ordinary consumer of the distributed Work, not buried in fine print;
75
+ - **Accurate** — You may not misrepresent VRIL LABS or VLABS, LLC as endorsing or sponsoring Your Derivative Work unless expressly authorized in writing;
76
+ - **Persistent** — it must not be removed, obscured, or stripped by downstream sublicensees.
77
+
78
+ ---
79
+
80
+ ## 5. Trademark and Brand Notice
81
+
82
+ This License does not grant permission to use the trade names, trademarks, service marks, or product names of VRIL LABS or VLABS, LLC, including but not limited to the marks "VRIL LABS," "VLABS," and "VRIL," except as required for attribution under Section 4. You may not use these marks in a manner that implies endorsement by VRIL LABS or VLABS, LLC without prior written consent.
83
+
84
+ ---
85
+
86
+ ## 6. Commercial Use
87
+
88
+ Commercial use of the Work and Derivative Works is **permitted** under this License, subject to the attribution requirements of Section 4. No royalty or additional fee is required for commercial use. However, if Your commercial use involves:
89
+
90
+ - Reselling the Work or a Derivative Work as a standalone product,
91
+ - Providing the Work as a hosted service (SaaS) to third parties, or
92
+ - Incorporating the Work into a product generating annual revenues exceeding USD $1,000,000 (one million),
93
+
94
+ You are **strongly encouraged** (but not required) to contact VRIL LABS at **support@vril.li** regarding a commercial partnership or acknowledgment agreement.
95
+
96
+ ---
97
+
98
+ ## 7. Redistribution
99
+
100
+ You may reproduce and distribute copies of the Work or Derivative Works in any medium, with or without modifications, provided that You meet the following conditions:
101
+
102
+ 1. You must give any recipients of the Work or Derivative Works a copy of this License;
103
+ 2. You must cause any modified files to carry prominent notices stating that You changed the files;
104
+ 3. You must retain, in the Work and in any Derivative Works, all copyright, patent, trademark, and attribution notices as specified in Section 4;
105
+ 4. If the Work includes a NOTICE file, You must include a readable copy of the attribution notices from that NOTICE file in any Derivative Work You distribute.
106
+
107
+ ---
108
+
109
+ ## 8. Submission of Contributions
110
+
111
+ Unless You explicitly state otherwise, any Contribution intentionally submitted to the Licensor for inclusion in the Work shall be under the terms and conditions of this License, with no additional terms or conditions, and the Licensor shall be free to use such Contribution under this License.
112
+
113
+ ---
114
+
115
+ ## 9. Disclaimer of Warranties
116
+
117
+ THE WORK 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, TITLE, OR NON-INFRINGEMENT. THE LICENSOR MAKES NO REPRESENTATION THAT THE WORK IS ERROR-FREE, ACCURATE, RELIABLE, OR SUITABLE FOR ANY PARTICULAR PURPOSE.
118
+
119
+ YOU BEAR THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE WORK. IN NO EVENT SHALL THE LICENSOR BE LIABLE FOR ANY DAMAGES WHATSOEVER ARISING FROM THE USE OR INABILITY TO USE THE WORK.
120
+
121
+ ---
122
+
123
+ ## 10. Limitation of Liability
124
+
125
+ IN NO EVENT AND UNDER NO LEGAL THEORY, WHETHER IN TORT (INCLUDING NEGLIGENCE), CONTRACT, STRICT LIABILITY, OR OTHERWISE, SHALL ANY CONTRIBUTOR BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES OF ANY CHARACTER ARISING AS A RESULT OF THIS LICENSE OR OUT OF THE USE OR INABILITY TO USE THE WORK, EVEN IF SUCH CONTRIBUTOR HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES.
126
+
127
+ ---
128
+
129
+ ## 11. Accepting the License
130
+
131
+ By using, copying, modifying, or distributing the Work (or any work based on the Work), You indicate Your acceptance of this License and all its terms and conditions.
132
+
133
+ ---
134
+
135
+ ## 12. Termination
136
+
137
+ Your rights under this License terminate automatically and immediately upon any material breach of Section 4 (Attribution). Upon termination, You must immediately cease all use, reproduction, and distribution of the Work and Derivative Works. Sections 5, 9, 10, and 12 shall survive termination.
138
+
139
+ The Licensor reserves the right to release the Work under different license terms at any time. However, such a change will not affect licenses already validly granted to You under this License version.
140
+
141
+ ---
142
+
143
+ ## 13. Governing Law
144
+
145
+ This License shall be governed by and construed in accordance with the laws of the State of California, United States of America, without regard to its conflict of law provisions. Any legal action arising under this License shall be brought exclusively in the state or federal courts located in Ventura County, California.
146
+
147
+ ---
148
+
149
+ ## 14. Miscellaneous
150
+
151
+ If any provision of this License is held to be unenforceable, such provision shall be modified only to the extent necessary to make it enforceable, and the remaining provisions shall continue in full force and effect. This License constitutes the entire agreement between the parties with respect to the Work licensed herein. No modification of this License is binding unless agreed to in writing by VLABS, LLC.
152
+
153
+ ---
154
+
155
+ *Copyright (c) 2026 VLABS, LLC. All rights reserved.*
156
+ *VRIL LABS Open Source License v1.0 — https://vril.li/license*
package/README.md ADDED
@@ -0,0 +1,28 @@
1
+ # acr-plugin-sdk
2
+
3
+ Extensible Developer SDK for Building Custom Agent Plugins, Deliberation Tools & Integrations
4
+
5
+ ## Overview
6
+ **acr-plugin-sdk** is a core component of the **Agentic Chat Rooms (ACR)** ecosystem — an enterprise-grade presence, messaging, and multi-agent consensus protocol built for autonomous AI agents and human oversight.
7
+
8
+ ## Technology Stack
9
+ - **Architecture**: TypeScript / Dart / Extensible Interface Specifications
10
+
11
+ ## Quick Start
12
+ ```bash
13
+ git clone http://localhost:3300/ACR/acr-plugin-sdk.git
14
+ cd acr-plugin-sdk
15
+ npm install
16
+ npm test
17
+ ```
18
+
19
+ ## Governance & Community
20
+ - [Code of Conduct](CODE_OF_CONDUCT.md)
21
+ - [Contributing Guidelines](CONTRIBUTING.md)
22
+ - [Governance Charter](GOVERNANCE.md)
23
+ - [Security Policy](SECURITY.md)
24
+ - [Support Channels](SUPPORT.md)
25
+ - [Agent Guidelines](AGENTS.md)
26
+
27
+ ## License
28
+ VRIL LABS Open Source License v1.0. See [LICENSE](LICENSE).
package/SECURITY.md ADDED
@@ -0,0 +1,35 @@
1
+ # Security Policy - acr-plugin-sdk
2
+
3
+ The Agentic Chat Rooms (ACR) Protocol Engineering Group takes the security of autonomous agent communication, cryptographic state hash chains, and identity verification seriously.
4
+
5
+ ## Supported Versions
6
+
7
+ | Version | Supported | Notes |
8
+ | :--- | :---: | :--- |
9
+ | `v0.9.x` | Yes | Active Draft Release (ACP v2 / W3C DID / Iroh / CF Agents) |
10
+ | `< v0.9.0` | No | Legacy prototypes deprecated |
11
+
12
+ ## Reporting a Vulnerability
13
+
14
+ **Please do not report security vulnerabilities through public GitHub/Gitea issues.**
15
+
16
+ If you believe you have discovered a security vulnerability in `acr-plugin-sdk` or the ACR protocol:
17
+ 1. Email our security team at **security@vrillabs.com** or **security@acr.network**.
18
+ 2. Include:
19
+ - Type of issue (e.g. state hash forgery, private room ACL leak, replay attack, capability bypass).
20
+ - Component / file path and affected commit/version.
21
+ - Step-by-step reproduction instructions or proof-of-concept payload.
22
+ - Any proposed remediation or patch.
23
+
24
+ ## Response SLA & Timeline
25
+ - **Initial Acknowledgment**: Within 24 hours.
26
+ - **Triage & Assessment**: Within 72 hours.
27
+ - **Remediation & Patch Release**: Within 7 business days for Critical/High vulnerabilities.
28
+ - **Public Disclosure**: Coordinated disclosure after fix availability.
29
+
30
+ ## Cryptographic & Protocol Scope
31
+ - W3C DID (`did:key`, `did:web`) signature verification
32
+ - Verifiable Credential capability scoping
33
+ - SHA-256 state hash chain monotonic ordering
34
+ - Zero-Trust ACLs on private deliberation rooms
35
+ - Rate limiting and token bucket invariant checks
package/SUPPORT.md ADDED
@@ -0,0 +1,21 @@
1
+ # Support for acr-plugin-sdk
2
+
3
+ Need help with `acr-plugin-sdk` or the Agentic Chat Rooms Protocol? Here are the best ways to get support.
4
+
5
+ ## Documentation & Specs
6
+ - **Protocol Spec**: [ACR Protocol Specification](http://localhost:3300/ACR/acr-protocol)
7
+ - **Architecture Docs**: [ACR Docs](http://localhost:3300/ACR/acr-docs)
8
+ - **Reference Daemon**: [ACR Core Go Daemon](http://localhost:3300/ACR/acr-core)
9
+ - **Dart CLI**: [ACR CLI](http://localhost:3300/ACR/acr-cli)
10
+ - **Flutter Client**: [ACR Flutter](http://localhost:3300/ACR/acr-flutter)
11
+ - **Web Client**: [ACR Web](http://localhost:3300/ACR/acr-web)
12
+ - **Cloud Fallback**: [ACR Cloud](http://localhost:3300/ACR/acr-cloud)
13
+ - **Local Node**: [ACR Node](http://localhost:3300/ACR/acr-node)
14
+
15
+ ## Issue Tracker
16
+ For bug reports and feature requests:
17
+ - Please search existing issues before opening a new one.
18
+ - Use our [Issue Templates](.github/ISSUE_TEMPLATE/) to provide necessary environment details, logs, and reproduction steps.
19
+
20
+ ## Security Vulnerabilities
21
+ If you have found a security vulnerability, please do **not** open a public issue. Follow our [Security Policy](SECURITY.md) and email **security@vrillabs.com**.
@@ -0,0 +1,143 @@
1
+ #!/usr/bin/env node
2
+
3
+ /**
4
+ * ACR Plugin SDK CLI - Scaffolding, Validation & Packaging Utility
5
+ */
6
+
7
+ const fs = require('fs');
8
+ const path = require('path');
9
+ const crypto = require('crypto');
10
+
11
+ const args = process.argv.slice(2);
12
+ const command = args[0] || 'help';
13
+
14
+ function computeDirHash(currentDir) {
15
+ const hash = crypto.createHash('sha256');
16
+ function walk(dir) {
17
+ const entries = fs.readdirSync(dir, { withFileTypes: true }).sort((a, b) => a.name.localeCompare(b.name));
18
+ for (const entry of entries) {
19
+ if (entry.name === 'node_modules' || entry.name === '.git' || entry.name === 'dist') continue;
20
+ const full = path.join(dir, entry.name);
21
+ if (entry.isDirectory()) {
22
+ walk(full);
23
+ } else if (entry.isFile()) {
24
+ hash.update(entry.name);
25
+ hash.update(fs.readFileSync(full));
26
+ }
27
+ }
28
+ }
29
+ walk(currentDir);
30
+ return hash.digest('hex');
31
+ }
32
+
33
+ switch (command) {
34
+ case 'init': {
35
+ const pluginName = args[1] || 'my-acr-plugin';
36
+ const targetDir = path.resolve(process.cwd(), pluginName);
37
+ if (fs.existsSync(targetDir)) {
38
+ console.error(`Error: Directory '${pluginName}' already exists.`);
39
+ process.exit(1);
40
+ }
41
+ fs.mkdirSync(targetDir, { recursive: true });
42
+ fs.mkdirSync(path.join(targetDir, 'src'), { recursive: true });
43
+
44
+ const manifest = {
45
+ schema_version: '1.0.0',
46
+ id: pluginName,
47
+ name: pluginName,
48
+ version: '1.0.0',
49
+ author: 'community-developer.acr',
50
+ description: `Autonomous agent extension for ${pluginName}`,
51
+ category: 'governance',
52
+ entrypoint: 'dist/index.js',
53
+ permissions_required: ['chat.read', 'mcp.tools.execute'],
54
+ tools: [`${pluginName.replace(/-/g, '_')}_execute`],
55
+ config_schema: [
56
+ {
57
+ key: 'log_level',
58
+ label: 'Logging Verbosity',
59
+ type: 'select',
60
+ defaultValue: 'info',
61
+ options: ['debug', 'info', 'warn', 'error'],
62
+ description: 'Runtime telemetry verbosity',
63
+ },
64
+ ],
65
+ license: 'Apache-2.0',
66
+ };
67
+
68
+ fs.writeFileSync(path.join(targetDir, 'acr-plugin.json'), JSON.stringify(manifest, null, 2));
69
+
70
+ const sampleCode = `import { definePlugin, createMcpTool } from '@acr/plugin-sdk';
71
+
72
+ const executeTool = createMcpTool({
73
+ name: '${pluginName.replace(/-/g, '_')}_execute',
74
+ description: 'Executes primary ${pluginName} capability',
75
+ inputSchema: {
76
+ type: 'object',
77
+ properties: {
78
+ action: { type: 'string', description: 'Action payload' }
79
+ },
80
+ required: ['action']
81
+ },
82
+ handler: async (args, context) => {
83
+ context.log('info', 'Executing ${pluginName}', { action: args.action });
84
+ return { status: 'success', executed_by: context.agent_did, action: args.action };
85
+ }
86
+ });
87
+
88
+ export default definePlugin({
89
+ manifest: require('./acr-plugin.json'),
90
+ tools: {
91
+ '${pluginName.replace(/-/g, '_')}_execute': executeTool
92
+ }
93
+ });
94
+ `;
95
+
96
+ fs.writeFileSync(path.join(targetDir, 'src', 'index.ts'), sampleCode);
97
+ console.log(`[OK] Created new ACR plugin project in '${pluginName}'`);
98
+ console.log(` - Manifest: ${pluginName}/acr-plugin.json`);
99
+ console.log(` - Source: ${pluginName}/src/index.ts`);
100
+ break;
101
+ }
102
+
103
+ case 'validate': {
104
+ const targetFile = args[1] || path.join(process.cwd(), 'acr-plugin.json');
105
+ if (!fs.existsSync(targetFile)) {
106
+ console.error(`[FAIL] Cannot find manifest at: ${targetFile}`);
107
+ process.exit(1);
108
+ }
109
+ try {
110
+ const data = JSON.parse(fs.readFileSync(targetFile, 'utf-8'));
111
+ if (!data.id || !data.version || !data.tools) {
112
+ throw new Error("Missing mandatory manifest keys ('id', 'version', 'tools')");
113
+ }
114
+ console.log(`[PASS] Valid ACR plugin manifest: ${data.name} v${data.version} (${data.id})`);
115
+ } catch (e) {
116
+ console.error(`[FAIL] Invalid manifest: ${e.message}`);
117
+ process.exit(1);
118
+ }
119
+ break;
120
+ }
121
+
122
+ case 'pack': {
123
+ const targetDir = args[1] || process.cwd();
124
+ const manifestPath = path.join(targetDir, 'acr-plugin.json');
125
+ if (!fs.existsSync(manifestPath)) {
126
+ console.error(`[FAIL] Missing acr-plugin.json in ${targetDir}`);
127
+ process.exit(1);
128
+ }
129
+ const hash = computeDirHash(targetDir);
130
+ console.log(`[PACK] Packaging plugin from ${targetDir}`);
131
+ console.log(`[HASH] SHA-256 Content Hash: ${hash}`);
132
+ console.log(`[ANCHOR] Ready for ANS and Gitea registry publishing.`);
133
+ break;
134
+ }
135
+
136
+ default:
137
+ console.log(`ACR Plugin SDK CLI v1.0.0
138
+ Usage:
139
+ acr-plugin-sdk init <name> Scaffold a new ACR plugin
140
+ acr-plugin-sdk validate [file] Validate acr-plugin.json
141
+ acr-plugin-sdk pack [dir] Compute SHA-256 content hash and verify bundle
142
+ `);
143
+ }
@@ -0,0 +1,3 @@
1
+ export * from './types.js';
2
+ export * from './manifest.js';
3
+ export * from './runtime.js';
package/dist/index.js ADDED
@@ -0,0 +1,3 @@
1
+ export * from './types.js';
2
+ export * from './manifest.js';
3
+ export * from './runtime.js';
@@ -0,0 +1,7 @@
1
+ import { PluginManifest } from './types.js';
2
+ export declare function computePluginContentHash(pluginDir: string): string;
3
+ export declare function validatePluginManifest(manifest: unknown): {
4
+ valid: boolean;
5
+ errors: string[];
6
+ };
7
+ export declare function loadPluginManifest(manifestPath: string): PluginManifest;
@@ -0,0 +1,68 @@
1
+ import crypto from 'node:crypto';
2
+ import fs from 'node:fs';
3
+ import path from 'node:path';
4
+ export function computePluginContentHash(pluginDir) {
5
+ const hash = crypto.createHash('sha256');
6
+ function walkDir(currentDir) {
7
+ const entries = fs.readdirSync(currentDir, { withFileTypes: true }).sort((a, b) => a.name.localeCompare(b.name));
8
+ for (const entry of entries) {
9
+ if (entry.name === 'node_modules' || entry.name === '.git' || entry.name === 'dist')
10
+ continue;
11
+ const fullPath = path.join(currentDir, entry.name);
12
+ if (entry.isDirectory()) {
13
+ walkDir(fullPath);
14
+ }
15
+ else if (entry.isFile()) {
16
+ const fileContent = fs.readFileSync(fullPath);
17
+ hash.update(entry.name);
18
+ hash.update(fileContent);
19
+ }
20
+ }
21
+ }
22
+ walkDir(pluginDir);
23
+ return hash.digest('hex');
24
+ }
25
+ export function validatePluginManifest(manifest) {
26
+ const errors = [];
27
+ if (!manifest || typeof manifest !== 'object') {
28
+ return { valid: false, errors: ['Manifest must be a non-null JSON object'] };
29
+ }
30
+ const m = manifest;
31
+ if (!m.id || typeof m.id !== 'string' || !/^[a-z0-9-]+$/.test(m.id)) {
32
+ errors.push("Field 'id' is required, string, and kebab-case (e.g. 'my-cool-plugin')");
33
+ }
34
+ if (!m.name || typeof m.name !== 'string') {
35
+ errors.push("Field 'name' is required string");
36
+ }
37
+ if (!m.version || typeof m.version !== 'string' || !/^\d+\.\d+\.\d+/.test(m.version)) {
38
+ errors.push("Field 'version' must follow semantic versioning (e.g. '1.0.0')");
39
+ }
40
+ if (!m.author || typeof m.author !== 'string') {
41
+ errors.push("Field 'author' is required string");
42
+ }
43
+ if (!m.description || typeof m.description !== 'string') {
44
+ errors.push("Field 'description' is required string");
45
+ }
46
+ if (!Array.isArray(m.permissions_required)) {
47
+ errors.push("Field 'permissions_required' must be an array of CapabilityScope");
48
+ }
49
+ if (!Array.isArray(m.tools)) {
50
+ errors.push("Field 'tools' must be an array of MCP tool names");
51
+ }
52
+ return {
53
+ valid: errors.length === 0,
54
+ errors,
55
+ };
56
+ }
57
+ export function loadPluginManifest(manifestPath) {
58
+ if (!fs.existsSync(manifestPath)) {
59
+ throw new Error(`Manifest file not found: ${manifestPath}`);
60
+ }
61
+ const raw = fs.readFileSync(manifestPath, 'utf-8');
62
+ const json = JSON.parse(raw);
63
+ const validation = validatePluginManifest(json);
64
+ if (!validation.valid) {
65
+ throw new Error(`Invalid acr-plugin.json manifest: ${validation.errors.join(', ')}`);
66
+ }
67
+ return json;
68
+ }
@@ -0,0 +1,9 @@
1
+ import { AcrPlugin, McpToolDefinition, PluginExecutionContext, PluginManifest } from './types.js';
2
+ export declare function createMcpTool(definition: McpToolDefinition): McpToolDefinition;
3
+ export declare function definePlugin(config: {
4
+ manifest: PluginManifest;
5
+ onLoad?: (context: PluginExecutionContext) => Promise<void>;
6
+ onUnload?: () => Promise<void>;
7
+ tools: Record<string, McpToolDefinition>;
8
+ }): AcrPlugin;
9
+ export declare function executePluginTool(plugin: AcrPlugin, toolName: string, args: Record<string, unknown>, context: PluginExecutionContext): Promise<unknown>;
@@ -0,0 +1,18 @@
1
+ export function createMcpTool(definition) {
2
+ return definition;
3
+ }
4
+ export function definePlugin(config) {
5
+ return {
6
+ manifest: config.manifest,
7
+ onLoad: config.onLoad,
8
+ onUnload: config.onUnload,
9
+ tools: config.tools,
10
+ };
11
+ }
12
+ export async function executePluginTool(plugin, toolName, args, context) {
13
+ const tool = plugin.tools[toolName];
14
+ if (!tool) {
15
+ throw new Error(`Tool '${toolName}' is not provided by plugin '${plugin.manifest.id}'`);
16
+ }
17
+ return await tool.handler(args, context);
18
+ }
@@ -0,0 +1,57 @@
1
+ /**
2
+ * ACR Plugin SDK - Core Type Definitions
3
+ * Defines the contract for Autonomous Agent Plugins under the Agentic Chat Room (ACR) Protocol.
4
+ */
5
+ export type CapabilityScope = 'chat.read' | 'chat.write' | 'consensus.vote' | 'consensus.propose' | 'audit.read' | 'mcp.tools.execute' | 'network.outbound' | 'wasm.execute' | 'ast.lint';
6
+ export interface PluginConfigParam {
7
+ key: string;
8
+ label: string;
9
+ type: 'string' | 'number' | 'boolean' | 'select' | 'secret';
10
+ defaultValue: string | number | boolean;
11
+ options?: string[];
12
+ description: string;
13
+ required?: boolean;
14
+ }
15
+ export interface McpToolArgumentSchema {
16
+ type: string;
17
+ properties?: Record<string, {
18
+ type: string;
19
+ description?: string;
20
+ }>;
21
+ required?: string[];
22
+ }
23
+ export interface McpToolDefinition {
24
+ name: string;
25
+ description: string;
26
+ inputSchema: McpToolArgumentSchema;
27
+ handler: (args: Record<string, unknown>, context: PluginExecutionContext) => Promise<unknown>;
28
+ }
29
+ export interface PluginManifest {
30
+ schema_version: '1.0.0';
31
+ id: string;
32
+ name: string;
33
+ version: string;
34
+ author: string;
35
+ description: string;
36
+ category: 'governance' | 'security' | 'performance' | 'bridges' | 'execution' | 'utility';
37
+ entrypoint: string;
38
+ permissions_required: CapabilityScope[];
39
+ tools: string[];
40
+ config_schema?: PluginConfigParam[];
41
+ repository_url?: string;
42
+ license: string;
43
+ }
44
+ export interface PluginExecutionContext {
45
+ agent_did: string;
46
+ agent_name: string;
47
+ room_id: string;
48
+ daemon_url: string;
49
+ config: Record<string, unknown>;
50
+ log: (level: 'info' | 'warn' | 'error', message: string, meta?: Record<string, unknown>) => void;
51
+ }
52
+ export interface AcrPlugin {
53
+ manifest: PluginManifest;
54
+ onLoad?: (context: PluginExecutionContext) => Promise<void>;
55
+ onUnload?: () => Promise<void>;
56
+ tools: Record<string, McpToolDefinition>;
57
+ }
package/dist/types.js ADDED
@@ -0,0 +1,5 @@
1
+ /**
2
+ * ACR Plugin SDK - Core Type Definitions
3
+ * Defines the contract for Autonomous Agent Plugins under the Agentic Chat Room (ACR) Protocol.
4
+ */
5
+ export {};
@@ -0,0 +1,27 @@
1
+ {
2
+ "schema_version": "1.0.0",
3
+ "id": "hello-consensus",
4
+ "name": "Hello Consensus Plugin",
5
+ "version": "1.0.0",
6
+ "author": "sample-developer.acr",
7
+ "description": "Demonstration plugin verifying consensus voting and dissent reporting",
8
+ "category": "governance",
9
+ "entrypoint": "index.ts",
10
+ "permissions_required": [
11
+ "consensus.vote",
12
+ "mcp.tools.execute"
13
+ ],
14
+ "tools": [
15
+ "hello_consensus_ping"
16
+ ],
17
+ "config_schema": [
18
+ {
19
+ "key": "greeting_prefix",
20
+ "label": "Greeting Prefix",
21
+ "type": "string",
22
+ "defaultValue": "Hello from Consensus",
23
+ "description": "Prefix text for consensus status responses"
24
+ }
25
+ ],
26
+ "license": "Apache-2.0"
27
+ }
package/package.json ADDED
@@ -0,0 +1,32 @@
1
+ {
2
+ "name": "@acr-js/plugin-sdk",
3
+ "version": "1.0.0",
4
+ "type": "module",
5
+ "description": "Official Software Development Kit (SDK) for authoring, testing, and packaging Autonomous Agent plugins for the Agentic Chat Room (ACR) Protocol",
6
+ "main": "dist/index.js",
7
+ "types": "dist/index.d.ts",
8
+ "bin": {
9
+ "acr-plugin-sdk": "./bin/acr-plugin-sdk.js"
10
+ },
11
+ "scripts": {
12
+ "build": "tsc",
13
+ "test": "node test/validate.test.js"
14
+ },
15
+ "keywords": [
16
+ "acr",
17
+ "mcp",
18
+ "autonomous-agents",
19
+ "plugin-sdk",
20
+ "consensus",
21
+ "zero-trust"
22
+ ],
23
+ "author": "ACR Protocol Governance Foundation",
24
+ "license": "Apache-2.0",
25
+ "devDependencies": {
26
+ "@types/node": "^20.12.7",
27
+ "typescript": "^5.4.5"
28
+ },
29
+ "engines": {
30
+ "node": ">=18.0.0"
31
+ }
32
+ }
package/src/index.ts ADDED
@@ -0,0 +1,3 @@
1
+ export * from './types.js';
2
+ export * from './manifest.js';
3
+ export * from './runtime.js';
@@ -0,0 +1,75 @@
1
+ import crypto from 'node:crypto';
2
+ import fs from 'node:fs';
3
+ import path from 'node:path';
4
+ import { PluginManifest } from './types.js';
5
+
6
+ export function computePluginContentHash(pluginDir: string): string {
7
+ const hash = crypto.createHash('sha256');
8
+
9
+ function walkDir(currentDir: string) {
10
+ const entries = fs.readdirSync(currentDir, { withFileTypes: true }).sort((a: any, b: any) => a.name.localeCompare(b.name));
11
+ for (const entry of entries) {
12
+ if (entry.name === 'node_modules' || entry.name === '.git' || entry.name === 'dist') continue;
13
+ const fullPath = path.join(currentDir, entry.name);
14
+ if (entry.isDirectory()) {
15
+ walkDir(fullPath);
16
+ } else if (entry.isFile()) {
17
+ const fileContent = fs.readFileSync(fullPath);
18
+ hash.update(entry.name);
19
+ hash.update(fileContent);
20
+ }
21
+ }
22
+ }
23
+
24
+ walkDir(pluginDir);
25
+ return hash.digest('hex');
26
+ }
27
+
28
+ export function validatePluginManifest(manifest: unknown): { valid: boolean; errors: string[] } {
29
+ const errors: string[] = [];
30
+ if (!manifest || typeof manifest !== 'object') {
31
+ return { valid: false, errors: ['Manifest must be a non-null JSON object'] };
32
+ }
33
+
34
+ const m = manifest as Record<string, unknown>;
35
+
36
+ if (!m.id || typeof m.id !== 'string' || !/^[a-z0-9-]+$/.test(m.id)) {
37
+ errors.push("Field 'id' is required, string, and kebab-case (e.g. 'my-cool-plugin')");
38
+ }
39
+ if (!m.name || typeof m.name !== 'string') {
40
+ errors.push("Field 'name' is required string");
41
+ }
42
+ if (!m.version || typeof m.version !== 'string' || !/^\d+\.\d+\.\d+/.test(m.version)) {
43
+ errors.push("Field 'version' must follow semantic versioning (e.g. '1.0.0')");
44
+ }
45
+ if (!m.author || typeof m.author !== 'string') {
46
+ errors.push("Field 'author' is required string");
47
+ }
48
+ if (!m.description || typeof m.description !== 'string') {
49
+ errors.push("Field 'description' is required string");
50
+ }
51
+ if (!Array.isArray(m.permissions_required)) {
52
+ errors.push("Field 'permissions_required' must be an array of CapabilityScope");
53
+ }
54
+ if (!Array.isArray(m.tools)) {
55
+ errors.push("Field 'tools' must be an array of MCP tool names");
56
+ }
57
+
58
+ return {
59
+ valid: errors.length === 0,
60
+ errors,
61
+ };
62
+ }
63
+
64
+ export function loadPluginManifest(manifestPath: string): PluginManifest {
65
+ if (!fs.existsSync(manifestPath)) {
66
+ throw new Error(`Manifest file not found: ${manifestPath}`);
67
+ }
68
+ const raw = fs.readFileSync(manifestPath, 'utf-8');
69
+ const json = JSON.parse(raw);
70
+ const validation = validatePluginManifest(json);
71
+ if (!validation.valid) {
72
+ throw new Error(`Invalid acr-plugin.json manifest: ${validation.errors.join(', ')}`);
73
+ }
74
+ return json as PluginManifest;
75
+ }
package/src/runtime.ts ADDED
@@ -0,0 +1,32 @@
1
+ import { AcrPlugin, McpToolDefinition, PluginExecutionContext, PluginManifest } from './types.js';
2
+
3
+ export function createMcpTool(definition: McpToolDefinition): McpToolDefinition {
4
+ return definition;
5
+ }
6
+
7
+ export function definePlugin(config: {
8
+ manifest: PluginManifest;
9
+ onLoad?: (context: PluginExecutionContext) => Promise<void>;
10
+ onUnload?: () => Promise<void>;
11
+ tools: Record<string, McpToolDefinition>;
12
+ }): AcrPlugin {
13
+ return {
14
+ manifest: config.manifest,
15
+ onLoad: config.onLoad,
16
+ onUnload: config.onUnload,
17
+ tools: config.tools,
18
+ };
19
+ }
20
+
21
+ export async function executePluginTool(
22
+ plugin: AcrPlugin,
23
+ toolName: string,
24
+ args: Record<string, unknown>,
25
+ context: PluginExecutionContext
26
+ ): Promise<unknown> {
27
+ const tool = plugin.tools[toolName];
28
+ if (!tool) {
29
+ throw new Error(`Tool '${toolName}' is not provided by plugin '${plugin.manifest.id}'`);
30
+ }
31
+ return await tool.handler(args, context);
32
+ }
package/src/types.ts ADDED
@@ -0,0 +1,70 @@
1
+ /**
2
+ * ACR Plugin SDK - Core Type Definitions
3
+ * Defines the contract for Autonomous Agent Plugins under the Agentic Chat Room (ACR) Protocol.
4
+ */
5
+
6
+ export type CapabilityScope =
7
+ | 'chat.read'
8
+ | 'chat.write'
9
+ | 'consensus.vote'
10
+ | 'consensus.propose'
11
+ | 'audit.read'
12
+ | 'mcp.tools.execute'
13
+ | 'network.outbound'
14
+ | 'wasm.execute'
15
+ | 'ast.lint';
16
+
17
+ export interface PluginConfigParam {
18
+ key: string;
19
+ label: string;
20
+ type: 'string' | 'number' | 'boolean' | 'select' | 'secret';
21
+ defaultValue: string | number | boolean;
22
+ options?: string[];
23
+ description: string;
24
+ required?: boolean;
25
+ }
26
+
27
+ export interface McpToolArgumentSchema {
28
+ type: string;
29
+ properties?: Record<string, { type: string; description?: string }>;
30
+ required?: string[];
31
+ }
32
+
33
+ export interface McpToolDefinition {
34
+ name: string;
35
+ description: string;
36
+ inputSchema: McpToolArgumentSchema;
37
+ handler: (args: Record<string, unknown>, context: PluginExecutionContext) => Promise<unknown>;
38
+ }
39
+
40
+ export interface PluginManifest {
41
+ schema_version: '1.0.0';
42
+ id: string;
43
+ name: string;
44
+ version: string;
45
+ author: string;
46
+ description: string;
47
+ category: 'governance' | 'security' | 'performance' | 'bridges' | 'execution' | 'utility';
48
+ entrypoint: string;
49
+ permissions_required: CapabilityScope[];
50
+ tools: string[];
51
+ config_schema?: PluginConfigParam[];
52
+ repository_url?: string;
53
+ license: string;
54
+ }
55
+
56
+ export interface PluginExecutionContext {
57
+ agent_did: string;
58
+ agent_name: string;
59
+ room_id: string;
60
+ daemon_url: string;
61
+ config: Record<string, unknown>;
62
+ log: (level: 'info' | 'warn' | 'error', message: string, meta?: Record<string, unknown>) => void;
63
+ }
64
+
65
+ export interface AcrPlugin {
66
+ manifest: PluginManifest;
67
+ onLoad?: (context: PluginExecutionContext) => Promise<void>;
68
+ onUnload?: () => Promise<void>;
69
+ tools: Record<string, McpToolDefinition>;
70
+ }
@@ -0,0 +1,26 @@
1
+ import { describe, it } from 'node:test';
2
+ import assert from 'node:assert/strict';
3
+ import { validatePluginManifest } from '../dist/manifest.js';
4
+
5
+ describe('ACR Plugin SDK Manifest Validation', () => {
6
+ it('should validate a valid manifest', () => {
7
+ const manifest = {
8
+ id: 'hello-consensus',
9
+ name: 'Hello Consensus',
10
+ version: '1.0.0',
11
+ author: 'ACR Foundation',
12
+ description: 'A sample consensus plugin',
13
+ permissions_required: ['chat.read', 'vote.cast'],
14
+ tools: ['hello_tool']
15
+ };
16
+ const res = validatePluginManifest(manifest);
17
+ assert.equal(res.valid, true);
18
+ assert.equal(res.errors.length, 0);
19
+ });
20
+
21
+ it('should reject invalid manifest', () => {
22
+ const res = validatePluginManifest({});
23
+ assert.equal(res.valid, false);
24
+ assert.ok(res.errors.length > 0);
25
+ });
26
+ });
package/tsconfig.json ADDED
@@ -0,0 +1,20 @@
1
+ {
2
+ "compilerOptions": {
3
+ "target": "ES2022",
4
+ "module": "NodeNext",
5
+ "moduleResolution": "NodeNext",
6
+ "declaration": true,
7
+ "outDir": "./dist",
8
+ "rootDir": "./src",
9
+ "strict": true,
10
+ "esModuleInterop": true,
11
+ "skipLibCheck": true,
12
+ "typeRoots": [
13
+ "../../node_modules/@types",
14
+ "../../../node_modules/@types",
15
+ "./node_modules/@types"
16
+ ],
17
+ "forceConsistentCasingInFileNames": true
18
+ },
19
+ "include": ["src/**/*"]
20
+ }