@nibgate/sdk 0.1.1 → 0.1.3
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/README.md +5 -0
- package/SKILL.md +163 -0
- package/package.json +3 -2
- package/src/browser/index.js +1 -1
- package/src/browser/reputation.js +5 -1
- package/src/index.d.ts +4 -0
package/README.md
CHANGED
|
@@ -17,6 +17,8 @@ import { createCircleGatewayServer, createNibgateServer } from '@nibgate/sdk/ser
|
|
|
17
17
|
|
|
18
18
|
This works with Next.js, React apps with an API backend, Express, NestJS, Remix, SvelteKit, Astro SSR, custom servers, and CMS/plugin environments. Plain HTML can use the widget and browser events, but real gating still requires a server, edge function, API route, or signed file endpoint.
|
|
19
19
|
|
|
20
|
+
Agents integrating Nibgate should read [`SKILL.md`](./SKILL.md) or the public copy at [https://nibgate.xyz/skill.md](https://nibgate.xyz/skill.md) for the compact operating guide.
|
|
21
|
+
|
|
20
22
|
## Usage
|
|
21
23
|
|
|
22
24
|
First paste the widget script from your Nibgate dashboard into your site:
|
|
@@ -164,6 +166,7 @@ const premiumGuide = {
|
|
|
164
166
|
let lastPayment = null;
|
|
165
167
|
|
|
166
168
|
const rating = createOnchainRating(premiumGuide, {
|
|
169
|
+
// Optional on Arc Testnet. The SDK defaults to NIBGATE_REPUTATION_CONTRACT.
|
|
167
170
|
contractAddress: process.env.NEXT_PUBLIC_NIBGATE_REPUTATION_CONTRACT,
|
|
168
171
|
siteId: process.env.NEXT_PUBLIC_NIBGATE_SITE_ID,
|
|
169
172
|
token: process.env.NEXT_PUBLIC_NIBGATE_SITE_TOKEN,
|
|
@@ -192,6 +195,8 @@ createEvmGatewayUnlock(premiumGuide, {
|
|
|
192
195
|
|
|
193
196
|
The lower-level `rateContentOnchain(resource, options)` function is also exported for custom UIs.
|
|
194
197
|
|
|
198
|
+
The SDK exports the current Arc Testnet reputation deployment as `NIBGATE_REPUTATION_CONTRACT`, plus `NIBGATE_REPUTATION_CHAIN_ID`, `NIBGATE_REPUTATION_CHAIN_NAME`, and `NIBGATE_REPUTATION_RPC_URL`. Pass `contractAddress` only when overriding the default deployment.
|
|
199
|
+
|
|
195
200
|
Ratings are proof-gated. Page views, time spent, scroll depth, and referrers are analytics signals; they should not become trust by themselves. Reputation-critical inputs use indexed onchain rating proofs. Signed ratings remain available only for local tests and migration tooling.
|
|
196
201
|
|
|
197
202
|
Nibgate reputation uses a versioned content identity:
|
package/SKILL.md
ADDED
|
@@ -0,0 +1,163 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: nibgate-sdk
|
|
3
|
+
description: Use when integrating, auditing, documenting, or modifying creator-owned paid content flows with the @nibgate/sdk package. Covers installing the package, adding the Nibgate widget, defining resources, protecting server routes, emitting content/unlock events, creating nibgate.json discovery metadata, wiring Circle Gateway/x402 one-time unlocks, and avoiding fake payment or client-only gating patterns.
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
# Nibgate SDK
|
|
7
|
+
|
|
8
|
+
Use `@nibgate/sdk` in the creator-owned site that actually serves the content. Nibgate Hub verifies the site, indexes public metadata, and records events; the creator site keeps the protected payload and payment receiver logic.
|
|
9
|
+
|
|
10
|
+
## Install
|
|
11
|
+
|
|
12
|
+
```bash
|
|
13
|
+
npm install @nibgate/sdk
|
|
14
|
+
```
|
|
15
|
+
|
|
16
|
+
Use browser helpers from `@nibgate/sdk` and access enforcement from `@nibgate/sdk/server`:
|
|
17
|
+
|
|
18
|
+
```ts
|
|
19
|
+
import { checkResourceAccess, setupResourcePage, trackResourcePage } from '@nibgate/sdk'
|
|
20
|
+
import { createCircleGatewayServer, manifestResponse } from '@nibgate/sdk/server'
|
|
21
|
+
```
|
|
22
|
+
|
|
23
|
+
## Site Widget
|
|
24
|
+
|
|
25
|
+
Paste the dashboard widget into the verified site layout:
|
|
26
|
+
|
|
27
|
+
```html
|
|
28
|
+
<script async src="https://nibgate.xyz/widget.js"
|
|
29
|
+
data-nibgate-site="site_..."
|
|
30
|
+
data-nibgate-token="ngv_..."
|
|
31
|
+
data-nibgate-api="https://api.nibgate.xyz">
|
|
32
|
+
</script>
|
|
33
|
+
```
|
|
34
|
+
|
|
35
|
+
The widget proves ownership and receives browser-side content, view, unlock, receipt, and reputation events. If the widget loads after app code, package events queue and flush when ready.
|
|
36
|
+
|
|
37
|
+
## Resource Shape
|
|
38
|
+
|
|
39
|
+
Define one stable resource per paid route, CMS row, media item, file, or API product:
|
|
40
|
+
|
|
41
|
+
```ts
|
|
42
|
+
const resource = {
|
|
43
|
+
id: post.id,
|
|
44
|
+
title: post.title,
|
|
45
|
+
description: post.excerpt,
|
|
46
|
+
type: 'article',
|
|
47
|
+
price: '0.01',
|
|
48
|
+
currency: 'USDC',
|
|
49
|
+
recipient: post.creatorWallet,
|
|
50
|
+
path: `/posts/${post.slug}`,
|
|
51
|
+
url: `https://creator.example/posts/${post.slug}`,
|
|
52
|
+
tags: ['essay', 'research'],
|
|
53
|
+
access: { humans: 'paid', agents: 'paid' },
|
|
54
|
+
unlock: { mode: 'one_time' }
|
|
55
|
+
}
|
|
56
|
+
```
|
|
57
|
+
|
|
58
|
+
Allowed public content types are `article`, `image`, `music`, and `video`. Use stable external ids; changing ids breaks continuity for Explore, receipts, and reputation.
|
|
59
|
+
|
|
60
|
+
## Discovery Metadata
|
|
61
|
+
|
|
62
|
+
Expose public metadata at `/nibgate.json`:
|
|
63
|
+
|
|
64
|
+
```ts
|
|
65
|
+
import { manifestResponse } from '@nibgate/sdk/server'
|
|
66
|
+
|
|
67
|
+
export function GET() {
|
|
68
|
+
return manifestResponse({
|
|
69
|
+
origin: process.env.NIBGATE_SITE_ORIGIN,
|
|
70
|
+
resources: [resource]
|
|
71
|
+
})
|
|
72
|
+
}
|
|
73
|
+
```
|
|
74
|
+
|
|
75
|
+
Never include the protected payload in `nibgate.json`. It is only for public cards, indexing, and agent-readable discovery.
|
|
76
|
+
|
|
77
|
+
## Browser Page Wiring
|
|
78
|
+
|
|
79
|
+
Track the resource page and wire unlock UI:
|
|
80
|
+
|
|
81
|
+
```ts
|
|
82
|
+
import { setupResourcePage, trackResourcePage } from '@nibgate/sdk'
|
|
83
|
+
|
|
84
|
+
trackResourcePage(resource, { source: 'creator-site' })
|
|
85
|
+
|
|
86
|
+
setupResourcePage(resource, {
|
|
87
|
+
source: 'creator-site',
|
|
88
|
+
accessPath: '/api/nibgate/access',
|
|
89
|
+
payPath: '/api/nibgate/pay',
|
|
90
|
+
button: '[data-nibgate-unlock]',
|
|
91
|
+
status: '[data-nibgate-status]',
|
|
92
|
+
createPaymentSignature: walletGatewayAdapter.pay
|
|
93
|
+
})
|
|
94
|
+
```
|
|
95
|
+
|
|
96
|
+
For custom flows, use `checkResourceAccess(resource, options)` directly. The browser can start checkout and report state, but the server must verify payment and issue unlock proof before returning protected content.
|
|
97
|
+
|
|
98
|
+
## Server Access Route
|
|
99
|
+
|
|
100
|
+
Protect paid content in a server route, API handler, middleware, guard, or signed file endpoint:
|
|
101
|
+
|
|
102
|
+
```ts
|
|
103
|
+
import { createCircleGatewayServer } from '@nibgate/sdk/server'
|
|
104
|
+
|
|
105
|
+
const nibgate = createCircleGatewayServer({
|
|
106
|
+
origin: process.env.NIBGATE_SITE_ORIGIN,
|
|
107
|
+
secret: process.env.NIBGATE_SECRET,
|
|
108
|
+
network: process.env.NIBGATE_PAYMENT_NETWORK || 'eip155:5042002'
|
|
109
|
+
})
|
|
110
|
+
|
|
111
|
+
export function GET(request: Request) {
|
|
112
|
+
return nibgate.accessResponse(request, resource, {
|
|
113
|
+
getContent: async () => new Response(protectedHtml, {
|
|
114
|
+
headers: { 'content-type': 'text/html; charset=utf-8' }
|
|
115
|
+
})
|
|
116
|
+
})
|
|
117
|
+
}
|
|
118
|
+
```
|
|
119
|
+
|
|
120
|
+
The route should return a real `402 Payment Required` challenge until the request has a valid payment proof or signed unlock proof.
|
|
121
|
+
|
|
122
|
+
## Required Env Vars
|
|
123
|
+
|
|
124
|
+
Creator site:
|
|
125
|
+
|
|
126
|
+
```bash
|
|
127
|
+
NIBGATE_SITE_ORIGIN=https://creator.example
|
|
128
|
+
NIBGATE_SITE_ID=site_...
|
|
129
|
+
NIBGATE_SITE_TOKEN=ngv_...
|
|
130
|
+
NIBGATE_API_BASE=https://api.nibgate.xyz
|
|
131
|
+
NIBGATE_SECRET=server_only_unlock_secret
|
|
132
|
+
NIBGATE_PAYMENT_MODE=circle-gateway
|
|
133
|
+
NIBGATE_PAYMENT_NETWORK=eip155:5042002
|
|
134
|
+
NIBGATE_SELLER_ADDRESS=0xCreatorReceiver
|
|
135
|
+
```
|
|
136
|
+
|
|
137
|
+
Only expose values with `NEXT_PUBLIC_` or client-side env names when they are intentionally public, such as site id, public token, API base, or reputation contract address. Never ship `NIBGATE_SECRET`, private keys, R2 credentials, Resend keys, database URLs, or privileged payment credentials to browser code.
|
|
138
|
+
|
|
139
|
+
## Payments
|
|
140
|
+
|
|
141
|
+
For v1, treat `unlock.mode: 'one_time'` with Circle Gateway/x402 as the production path. A Gateway/x402 payment signature is a payment proof. A normal wallet message signature is not payment.
|
|
142
|
+
|
|
143
|
+
Use `NIBGATE_BUYER_PRIVATE_KEY` only in local demos or controlled tests. In production, the visitor or agent wallet signs/pays the returned `PAYMENT-REQUIRED` challenge.
|
|
144
|
+
|
|
145
|
+
## Reputation
|
|
146
|
+
|
|
147
|
+
After a verified unlock, rating UI can submit onchain ratings for the same resource. Reputation-critical inputs should be tied to unlock/payment proof and indexed from chain activity. Page views, scroll depth, and referrers are analytics signals, not trust by themselves.
|
|
148
|
+
|
|
149
|
+
## Never Do These
|
|
150
|
+
|
|
151
|
+
- Do not hide paid HTML with CSS or client state after rendering it publicly.
|
|
152
|
+
- Do not fake payment ids, receipts, unlocks, or successful access.
|
|
153
|
+
- Do not replace Gateway/x402 payment signatures with ordinary wallet message signatures.
|
|
154
|
+
- Do not store backend secrets in browser env vars.
|
|
155
|
+
- Do not let mutable titles or slugs be the only resource identity.
|
|
156
|
+
- Do not expose private content in `nibgate.json`, meta tags, JSON-LD, page source, or static builds.
|
|
157
|
+
|
|
158
|
+
## Framework Notes
|
|
159
|
+
|
|
160
|
+
- **Next.js**: use route handlers for `/nibgate.json` and `/api/nibgate/access`; protect content before rendering paid payloads.
|
|
161
|
+
- **Express/NestJS**: use middleware, controllers, or guards around protected routes.
|
|
162
|
+
- **Astro/SvelteKit/Remix**: use SSR/server routes or endpoints; plain static builds need a protected API or signed URL for private payloads.
|
|
163
|
+
- **CMS apps**: save Nibgate resource settings beside each content record, including type, price, currency, receiver wallet, access policy, unlock mode, and discovery preference.
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@nibgate/sdk",
|
|
3
|
-
"version": "0.1.
|
|
3
|
+
"version": "0.1.3",
|
|
4
4
|
"description": "Framework-agnostic browser and server package for creator-owned gated content, unlock events, and receipts.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"sideEffects": false,
|
|
@@ -39,7 +39,8 @@
|
|
|
39
39
|
},
|
|
40
40
|
"files": [
|
|
41
41
|
"src",
|
|
42
|
-
"README.md"
|
|
42
|
+
"README.md",
|
|
43
|
+
"SKILL.md"
|
|
43
44
|
],
|
|
44
45
|
"keywords": [
|
|
45
46
|
"nibgate",
|
package/src/browser/index.js
CHANGED
|
@@ -75,7 +75,7 @@ export function rateResource(resource, rating = {}, extra = {}) {
|
|
|
75
75
|
return emit('content_rating', payload);
|
|
76
76
|
}
|
|
77
77
|
|
|
78
|
-
export { contentRatingHash, NIBGATE_CONTENT_HASH_NAMESPACE, NIBGATE_REPUTATION_ABI, rateContentOnchain, reviewTextHash } from './reputation.js';
|
|
78
|
+
export { contentRatingHash, NIBGATE_CONTENT_HASH_NAMESPACE, NIBGATE_REPUTATION_ABI, NIBGATE_REPUTATION_CHAIN_ID, NIBGATE_REPUTATION_CHAIN_NAME, NIBGATE_REPUTATION_CONTRACT, NIBGATE_REPUTATION_RPC_URL, rateContentOnchain, reviewTextHash } from './reputation.js';
|
|
79
79
|
|
|
80
80
|
export function trackResourcePage(resource, options = {}) {
|
|
81
81
|
const item = createGate(resource, options.gateOptions || {});
|
|
@@ -6,6 +6,10 @@ const RATE_CONTENT_SELECTOR = '0xc62fad09';
|
|
|
6
6
|
const ZERO_HASH = `0x${'0'.repeat(64)}`;
|
|
7
7
|
|
|
8
8
|
export const NIBGATE_CONTENT_HASH_NAMESPACE = 'nibgate:content:v1';
|
|
9
|
+
export const NIBGATE_REPUTATION_CHAIN_ID = 5042002;
|
|
10
|
+
export const NIBGATE_REPUTATION_CHAIN_NAME = 'Arc Testnet';
|
|
11
|
+
export const NIBGATE_REPUTATION_RPC_URL = 'https://rpc.testnet.arc.network';
|
|
12
|
+
export const NIBGATE_REPUTATION_CONTRACT = '0x9f27fd62e75f86a3c7addfdba443aab1f930e281';
|
|
9
13
|
|
|
10
14
|
export const NIBGATE_REPUTATION_ABI = [
|
|
11
15
|
{
|
|
@@ -105,7 +109,7 @@ export async function rateContentOnchain(resource, options = {}) {
|
|
|
105
109
|
const provider = options.provider || globalThis?.ethereum;
|
|
106
110
|
if (!provider?.request) throw new Error('Connect an EVM wallet to rate this content onchain.');
|
|
107
111
|
|
|
108
|
-
const contractAddress = options.contractAddress || options.reputationContract;
|
|
112
|
+
const contractAddress = options.contractAddress || options.reputationContract || NIBGATE_REPUTATION_CONTRACT;
|
|
109
113
|
if (!contractAddress) throw new Error('Nibgate reputation contract address is not configured.');
|
|
110
114
|
|
|
111
115
|
const accounts = await provider.request({ method: 'eth_requestAccounts' });
|
package/src/index.d.ts
CHANGED
|
@@ -411,6 +411,10 @@ export declare function setupResourcePage(resource: NibgateResource | string, op
|
|
|
411
411
|
export declare function rateResource(resource: NibgateResource | string, rating?: NibgateRating | number, extra?: Record<string, unknown>): boolean;
|
|
412
412
|
export declare const NIBGATE_REPUTATION_ABI: readonly unknown[];
|
|
413
413
|
export declare const NIBGATE_CONTENT_HASH_NAMESPACE: 'nibgate:content:v1';
|
|
414
|
+
export declare const NIBGATE_REPUTATION_CHAIN_ID: 5042002;
|
|
415
|
+
export declare const NIBGATE_REPUTATION_CHAIN_NAME: 'Arc Testnet';
|
|
416
|
+
export declare const NIBGATE_REPUTATION_RPC_URL: 'https://rpc.testnet.arc.network';
|
|
417
|
+
export declare const NIBGATE_REPUTATION_CONTRACT: '0x9f27fd62e75f86a3c7addfdba443aab1f930e281';
|
|
414
418
|
export declare function contentRatingHash(resource: NibgateResource | string, options?: Record<string, unknown>): string;
|
|
415
419
|
export declare function reviewTextHash(review?: string): string;
|
|
416
420
|
export declare function rateContentOnchain(resource: NibgateResource | string, options: NibgateOnchainRatingOptions): Promise<NibgateOnchainRatingResult>;
|