@seasonkoh/webaz 0.1.22 → 0.1.24

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.
@@ -22,7 +22,7 @@ export function buildEconomicParticipation(getParam) {
22
22
  note: 'RFC-011 §⑧. The roles by which an external actor enters the protocol VALUE flow (earns fees / posts collateral / bears conserved liability) — the highest liability tier (value_participant). Rates & thresholds are read LIVE from protocol_params at request time (doc=code: this index can never drift from the enforced economics). Honesty: roles marked status=live are enforced today; status=scaffolded means the hook exists but generic third-party onboarding awaits its own RFC + real demand (enters-core test).',
23
23
  principles: {
24
24
  fairness: ['public & transparent', 'liability follows the responsible party', 'zero cost to the faultless party'],
25
- conservation: 'Every settlement conserves value: a forfeit F is REDISTRIBUTED (protocol ≤ its fee, fund_base excluded / buyer up to 50% / promoters capped at original commission / residual commission_reserve) — never minted. See engine.settleFault.',
25
+ conservation: 'Every settlement conserves value: a forfeit F is REDISTRIBUTED (protocol ≤ its fee, fund_base excluded / promoters capped at their original commission / the harmed buyer gets 50% of the post-fee remainder AND absorbs any unused-commission residual so the buyer can exceed 50%) — never minted. See engine.settleFault.',
26
26
  bootstrap_no_forfeit: 'RFC-008: an order with stake_backing=0 (bootstrap / require_seller_stake=0) incurs ZERO forfeit and never touches the participant\'s free balance. Real forfeit applies only to staked orders.',
27
27
  },
28
28
  enter_value_flow: 'A value participant is in the accountability net via api_key→passport AND collateral/reputation-bound. Highest liability tier. See /.well-known/webaz-integration.json#liability_tiers.value_participant.',
@@ -15,10 +15,14 @@ export function buildIntegrationContract() {
15
15
  contract_version: CONTRACT_VERSION,
16
16
  software_version: SOFTWARE_VERSION,
17
17
  thesis: 'WebAZ is agent-native: you integrate by your agent reading this machine-readable contract and self-integrating — we do NOT build a bespoke API/auth/webhook layer per integrator. The protocol provides rules + semantics + boundaries + accountability + eventing + verifiability + settlement. See docs/RFC-011.',
18
+ // 源码仓库 launch 前私有 —— 公开声明,防"自称开源但 GitHub 404"被读成 vaporware。
19
+ source_status: 'The source repo (github.com/seasonsagents-art/webaz) is PRIVATE until the W8 public launch, so GitHub links in these surfaces may return 404 until then — they open at launch, not a dead project. The full machine-readable spec is ALREADY public via these /.well-known/* surfaces; an agent never needs the repo to integrate or verify.',
18
20
  // 外部 agent 的第一道问题:"我怎么从匿名读升到能写?" —— 入口必须自答(不依赖 GitHub)。
19
21
  access: {
22
+ browse_first: 'No account needed to START: browse the live catalog at https://webaz.xyz/#discover and read every well-known surface below anonymously. Try before you commit.',
20
23
  anonymous_read: 'no credential needed — public GET endpoints + the well-known surfaces below.',
21
24
  get_api_key: 'an api_key requires a REAL HUMAN to register at https://webaz.xyz (invite code + Passkey). Agents CANNOT self-register — this is the accountability root ("every agent has an accountable human behind it"). After the human gets the key, set it as the agent\'s bearer token.',
25
+ how_to_get_invite: 'Pre-launch is invite-gated for Sybil resistance. Request one by leaving your email at https://webaz.xyz/#welcome (or email contact@webaz.xyz). You can browse + read everything WITHOUT an invite — it is only needed to register and write.',
22
26
  then: 'declare your write scope at POST /api/me/agents/declarations (scope tokens from the capability matrix §②); a Passkey-bound human is exempt from scope declaration. See onboarding (③).',
23
27
  tiers: 'anonymous_read → authenticated_write (api_key→passport) → value_participant (collateral). See liability_tiers below.',
24
28
  },
@@ -36,7 +36,8 @@
36
36
  <p><strong>For buyers:</strong> funds are held in escrow and released only after you confirm receipt; sellers who don't accept/ship/deliver in time trigger an automatic refund; disputes are decided with evidence + neutral arbitration; seller reputation, price history and arbitration precedents are public before you buy.</p>
37
37
  <p><strong>For AI agents:</strong> browse, compare, order and track fulfillment via the Model Context Protocol (MCP). Protocol state is public at <a href="/.well-known/webaz-protocol.json">/.well-known/webaz-protocol.json</a>; the integration contract is at <a href="/.well-known/webaz-integration.json">/.well-known/webaz-integration.json</a>.</p>
38
38
  <p><strong>Status:</strong> pre-launch — WAZ is a simulated test currency; no real money settles yet.</p>
39
- <p>Browse: <a href="/#discover">/#discover</a> · Learn more: <a href="/#welcome">/#welcome</a> · Source: <a href="https://github.com/seasonsagents-art/webaz">github.com/seasonsagents-art/webaz</a></p>
39
+ <p><strong>Browse now — no account needed:</strong> <a href="/#discover">/#discover</a> · <strong>Want in?</strong> Pre-launch is invite-gated; request an invite (leave your email) at <a href="/#welcome">/#welcome</a>.</p>
40
+ <p style="color:#6b7280;font-size:14px">Source repo opens at public launch — <a href="https://github.com/seasonsagents-art/webaz">github.com/seasonsagents-art/webaz</a> may 404 until then; the full machine-readable spec is already public at <a href="/.well-known/webaz-integration.json">/.well-known/webaz-integration.json</a>.</p>
40
41
  <p style="color:#6b7280;font-size:14px">This page is an interactive app and needs JavaScript for full functionality.</p>
41
42
  </main>
42
43
  </noscript>
@@ -91,6 +91,21 @@ export function registerPublicUtilsRoutes(app, deps) {
91
91
  // software_version = 本代码 npm/release semver(= package.json,自动同步,永不漂移)
92
92
  schema_version: CONTRACT_VERSION,
93
93
  software_version: SOFTWARE_VERSION,
94
+ // 给【终端用户/买家】的一句话价值主张 —— 陌生 agent / 爬虫抓 manifest 第一眼就懂"对买家有什么用",
95
+ // 不只是抽象 tagline + 技术 description。与 MCP webaz_info.for_end_user 对齐(两个发现面一致)。
96
+ for_end_user: {
97
+ one_liner: 'Shop with built-in protection: every order is escrow-held and only released after you confirm receipt; if the seller is late, you are auto-refunded. / 自带保护的购物:每笔订单托管,确认收货才放款;卖家超时自动退款给你。',
98
+ why_use: [
99
+ 'Escrow on every order — money released only after you confirm receipt (or auto-confirm window).',
100
+ 'Automatic fault ruling — seller fails to accept/ship/deliver in time → auto-refund, no haggling.',
101
+ 'Disputes with evidence + neutral arbitration.',
102
+ 'Decision-ready transparency — seller reputation, price history and arbitration precedents are public before you buy.',
103
+ 'Agent-native — your AI agent can compare, order and track fulfillment via MCP.',
104
+ ],
105
+ honesty: 'Pre-launch: WAZ is a simulated test currency; no real money settles yet.',
106
+ try_it: 'Browse now, no account needed → https://webaz.xyz/#discover',
107
+ get_access: 'Want to register? Pre-launch is invite-gated — request an invite at https://webaz.xyz/#welcome (browsing needs no invite).',
108
+ },
94
109
  network_state: {
95
110
  phase,
96
111
  real_users_on_canonical: realUsers,
@@ -118,6 +133,8 @@ export function registerPublicUtilsRoutes(app, deps) {
118
133
  },
119
134
  // 公开披露文档(#1050) — 协议层"钱怎么流"的源真理(协议外可读)
120
135
  disclosures: {
136
+ // 源码仓库 launch 前私有,下列 github 链接可能 404(launch 时开),不是死项目;机器可读 spec 已全在 /.well-known/*。
137
+ source_status: 'repo private until W8 public launch — github.com links below may 404 until then (they open at launch); the full spec is already public via /.well-known/*.',
121
138
  economic_model: 'https://github.com/seasonsagents-art/webaz/blob/main/docs/ECONOMIC-MODEL.md',
122
139
  mlm_compliance: 'https://github.com/seasonsagents-art/webaz/blob/main/docs/MLM-COMPLIANCE.md',
123
140
  agent_governance: 'https://github.com/seasonsagents-art/webaz/blob/main/docs/AGENT-GOVERNANCE.md',
@@ -55,4 +55,85 @@ export function registerReferralRoutes(app, deps) {
55
55
  logAdminAction(admin.id, 'invite_rotation_toggle', 'system', 'invite_rotation_enabled', { value: v });
56
56
  res.json({ success: true, enabled: !!enabled });
57
57
  });
58
+ // RFC-003 #1122: 生成商品分享链接(把 MCP webaz_share_link 的本地计算搬到服务端,
59
+ // 让 MCP NETWORK 模式可代理)。RFC-002 §3.5 valuation-layer gate:需 rewards opt-in。
60
+ // 与 PWA pickPreferredSide 对齐的 side 选择(team_count | pv_count)。
61
+ app.get('/api/share-link', (req, res) => {
62
+ const user = auth(req, res);
63
+ if (!user)
64
+ return;
65
+ const userId = user.id;
66
+ const productId = String(req.query.product_id || '');
67
+ const sideArg = String(req.query.side || 'auto');
68
+ if (!productId)
69
+ return void res.status(400).json({ error: 'product_id required', error_code: 'PRODUCT_ID_REQUIRED' });
70
+ const optIn = db.prepare("SELECT rewards_opted_in FROM users WHERE id = ?").get(userId)?.rewards_opted_in ?? 0;
71
+ if (optIn !== 1) {
72
+ const getParam = (key, def) => {
73
+ const r = db.prepare("SELECT value FROM protocol_params WHERE key = ?").get(key);
74
+ return r ? Number(r.value) : def;
75
+ };
76
+ const minOrders = getParam('rewards_opt_in.min_completed_orders', 1);
77
+ const requirePasskey = getParam('rewards_opt_in.require_passkey', 1);
78
+ const totalCompleted = db.prepare("SELECT COUNT(*) as n FROM orders WHERE buyer_id = ? AND status = 'completed'").get(userId).n;
79
+ const passkeyCount = db.prepare("SELECT COUNT(*) as n FROM webauthn_credentials WHERE user_id = ?").get(userId).n;
80
+ const missing = [];
81
+ if (totalCompleted < minOrders)
82
+ missing.push(`completed_orders ${totalCompleted}/${minOrders}`);
83
+ if (requirePasskey === 1 && passkeyCount === 0)
84
+ missing.push('passkey_not_registered');
85
+ if (missing.length === 0)
86
+ missing.push('application_not_submitted');
87
+ return void res.status(403).json({
88
+ error: 'rewards_opt_in_required',
89
+ message: 'Share-link generation is a valuation-layer action — requires builder-identity opt-in (RFC-002 §3.5)',
90
+ missing_requirements: missing,
91
+ next_steps: [
92
+ 'Open PWA #me → tap "申请共建身份 / Apply for builder identity"',
93
+ 'Read the 8-second disclosure (cannot skip)',
94
+ 'Submit application — pre-checks run server-side',
95
+ ],
96
+ });
97
+ }
98
+ const product = db.prepare("SELECT id, title, price, commission_rate FROM products WHERE id = ? AND status='active'").get(productId);
99
+ if (!product)
100
+ return void res.status(404).json({ error: '商品不存在或已下架', error_code: 'PRODUCT_NOT_FOUND' });
101
+ let side = 'right';
102
+ if (sideArg === 'left' || sideArg === 'right') {
103
+ side = sideArg;
104
+ }
105
+ else {
106
+ const u = db.prepare("SELECT placement_pref, total_left_pv, total_right_pv, left_count, right_count FROM users WHERE id = ?")
107
+ .get(userId);
108
+ const pref = u?.placement_pref || 'team_count';
109
+ if (pref === 'pv_count') {
110
+ const since = new Date(Date.now() - 90 * 24 * 60 * 60 * 1000).toISOString().slice(0, 19).replace('T', ' ');
111
+ const w = db.prepare(`SELECT COALESCE(SUM(consumed_left_pv),0) AS l, COALESCE(SUM(consumed_right_pv),0) AS r
112
+ FROM binary_score_records WHERE user_id = ? AND created_at >= ?`)
113
+ .get(userId, since);
114
+ const leftPv = Number(u?.total_left_pv ?? 0) + Number(w.l);
115
+ const rightPv = Number(u?.total_right_pv ?? 0) + Number(w.r);
116
+ side = leftPv <= rightPv ? 'left' : 'right';
117
+ }
118
+ else {
119
+ side = (Number(u?.left_count ?? 0) <= Number(u?.right_count ?? 0)) ? 'left' : 'right';
120
+ }
121
+ }
122
+ const completed = db.prepare("SELECT COUNT(*) as n FROM orders WHERE buyer_id = ? AND status = 'completed'").get(userId).n;
123
+ const override = db.prepare("SELECT l1_share_override FROM users WHERE id = ?").get(userId)?.l1_share_override ?? 0;
124
+ const canL1 = override === 1 || (override === 0 && completed > 0);
125
+ const rate = Number(product.commission_rate ?? 0);
126
+ const link = `/?ref=${userId}&side=${side}#order-product/${productId}`;
127
+ res.json({
128
+ product: { id: product.id, title: product.title, price: product.price, commission_rate: rate },
129
+ share_link: link,
130
+ full_url_hint: 'Prepend webaz.xyz (production) to get the absolute URL',
131
+ side,
132
+ binary_explanation: `New user via this link → placed in your ${side === 'left' ? '🔵 left' : '🟢 right'} subtree (tail anchor)`,
133
+ commission_eligibility: canL1
134
+ ? `You will earn 3-tier commission: L1=${(rate * 0.70 * 100).toFixed(1)}% L2=${(rate * 0.20 * 100).toFixed(1)}% L3=${(rate * 0.10 * 100).toFixed(1)}% of sale price`
135
+ : 'You are NOT verified yet (need 1 completed purchase). 3-tier commission will be skipped, but points-matching still builds.',
136
+ next_steps: 'Share on TikTok / WeChat / Telegram. New user clicks → 30-day attribution window starts.',
137
+ });
138
+ });
58
139
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@seasonkoh/webaz",
3
- "version": "0.1.22",
3
+ "version": "0.1.24",
4
4
  "description": "[PRE-LAUNCH] Agent-native decentralized commerce protocol. Humans and AI agents trade on the same protocol via MCP tools. ⚠️ Repository currently private until W8 public launch — GitHub links may return 404. See https://webaz.xyz for status.",
5
5
  "main": "dist/mcp.js",
6
6
  "bin": {