wolverine-ai 5.2.3 → 5.2.5

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "wolverine-ai",
3
- "version": "5.2.3",
3
+ "version": "5.2.5",
4
4
  "description": "Self-healing Node.js server framework powered by AI. Catches crashes, diagnoses errors, generates fixes, verifies, and restarts — automatically.",
5
5
  "main": "src/index.js",
6
6
  "bin": {
@@ -101,6 +101,7 @@ async function x402Plugin(fastify, opts) {
101
101
  asset: USDC_BASE,
102
102
  payTo: _payTo,
103
103
  maxTimeoutSeconds: 300,
104
+ extra: { name: "USD Coin", version: "2" }, // EIP-712 domain params for USDC
104
105
  };
105
106
  const paymentRequired = {
106
107
  x402Version: 2,
@@ -137,6 +138,7 @@ async function x402Plugin(fastify, opts) {
137
138
  asset: USDC_BASE,
138
139
  payTo: _payTo,
139
140
  maxTimeoutSeconds: 300,
141
+ extra: { name: "USD Coin", version: "2" },
140
142
  };
141
143
 
142
144
  // Decode the payment payload
@@ -205,66 +207,60 @@ async function x402Plugin(fastify, opts) {
205
207
 
206
208
  /**
207
209
  * Call the x402 facilitator — matches the exact format from @x402/core HTTPFacilitatorClient.
210
+ * Uses fetch() for automatic redirect following (x402.org → www.x402.org).
208
211
  *
209
212
  * POST {facilitatorUrl}/verify or /settle
210
213
  * Body: { x402Version, paymentPayload, paymentRequirements }
211
214
  */
212
215
  async function _facilitatorCall(endpoint, paymentPayload, paymentRequirements) {
213
216
  try {
214
- const https = require("https");
215
- const http = require("http");
216
- const url = new (require("url").URL)(_facilitatorUrl + endpoint);
217
+ const url = _facilitatorUrl + endpoint;
217
218
  const body = JSON.stringify({
218
219
  x402Version: paymentPayload.x402Version || 2,
219
220
  paymentPayload,
220
221
  paymentRequirements,
221
222
  });
222
223
 
223
- return new Promise((resolve) => {
224
- const client = url.protocol === "https:" ? https : http;
225
- const req = client.request({
226
- hostname: url.hostname,
227
- port: url.port,
228
- path: url.pathname,
229
- method: "POST",
230
- headers: { "Content-Type": "application/json", "Content-Length": Buffer.byteLength(body) },
231
- timeout: 30000,
232
- }, (res) => {
233
- let data = "";
234
- res.on("data", (c) => data += c);
235
- res.on("end", () => {
236
- try {
237
- const parsed = JSON.parse(data);
238
- if (res.statusCode >= 200 && res.statusCode < 300) {
239
- // Verify: check isValid. Settle: check success.
240
- if (endpoint === "/verify" && parsed.isValid === false) {
241
- resolve({ ok: false, reason: parsed.invalidReason || "verification_rejected", data: parsed });
242
- } else if (endpoint === "/settle" && parsed.success === false) {
243
- resolve({ ok: false, reason: parsed.errorReason || "settlement_rejected", data: parsed });
244
- } else {
245
- resolve({ ok: true, data: parsed });
246
- }
247
- } else {
248
- // Error response
249
- const reason = parsed.invalidReason || parsed.errorReason || parsed.error || `facilitator_${res.statusCode}`;
250
- console.log(` ⚠️ x402 facilitator ${endpoint} ${res.statusCode}: ${reason}`);
251
- resolve({ ok: false, reason, data: parsed });
252
- }
253
- } catch {
254
- resolve({ ok: false, reason: `facilitator_parse_error_${res.statusCode}` });
255
- }
256
- });
257
- });
258
- req.on("error", (err) => {
259
- console.log(` ⚠️ x402 facilitator ${endpoint} error: ${err.message}`);
260
- resolve({ ok: false, reason: "facilitator_unavailable: " + err.message });
261
- });
262
- req.on("timeout", () => { req.destroy(); resolve({ ok: false, reason: "facilitator_timeout" }); });
263
- req.write(body);
264
- req.end();
224
+ const controller = new AbortController();
225
+ const timeout = setTimeout(() => controller.abort(), 30000);
226
+
227
+ const response = await fetch(url, {
228
+ method: "POST",
229
+ headers: { "Content-Type": "application/json" },
230
+ body,
231
+ redirect: "follow",
232
+ signal: controller.signal,
265
233
  });
234
+
235
+ clearTimeout(timeout);
236
+ const text = await response.text();
237
+ let parsed;
238
+ try { parsed = JSON.parse(text); } catch {
239
+ console.log(` ⚠️ x402 facilitator ${endpoint} ${response.status}: unparseable response`);
240
+ return { ok: false, reason: `facilitator_parse_error_${response.status}` };
241
+ }
242
+
243
+ if (!response.ok) {
244
+ const reason = parsed.invalidReason || parsed.errorReason || parsed.error || `facilitator_${response.status}`;
245
+ console.log(` ⚠️ x402 facilitator ${endpoint} ${response.status}: ${reason}`);
246
+ return { ok: false, reason, data: parsed };
247
+ }
248
+
249
+ // Verify: check isValid. Settle: check success.
250
+ if (endpoint === "/verify" && parsed.isValid === false) {
251
+ console.log(` ⚠️ x402 verify rejected: ${parsed.invalidReason || "unknown"}`);
252
+ return { ok: false, reason: parsed.invalidReason || "verification_rejected", data: parsed };
253
+ }
254
+ if (endpoint === "/settle" && parsed.success === false) {
255
+ console.log(` ⚠️ x402 settle rejected: ${parsed.errorReason || "unknown"}`);
256
+ return { ok: false, reason: parsed.errorReason || "settlement_rejected", data: parsed };
257
+ }
258
+
259
+ return { ok: true, data: parsed };
266
260
  } catch (err) {
267
- return { ok: false, reason: "facilitator_error: " + err.message };
261
+ const reason = err.name === "AbortError" ? "facilitator_timeout" : "facilitator_unavailable: " + err.message;
262
+ console.log(` ⚠️ x402 facilitator ${endpoint}: ${reason}`);
263
+ return { ok: false, reason };
268
264
  }
269
265
  }
270
266