@nordsym/apiclaw 1.4.3 → 1.4.4
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/CHANGELOG.md +8 -0
- package/README.md +21 -1
- package/convex/http.ts +112 -18
- package/convex/logs.ts +25 -0
- package/convex/mou.ts +17 -0
- package/convex/searchLogs.ts +111 -106
- package/dist/cli/commands/doctor.d.ts.map +1 -1
- package/dist/cli/commands/doctor.js +45 -32
- package/dist/cli/commands/doctor.js.map +1 -1
- package/dist/cli/commands/setup.js +2 -2
- package/dist/cli/commands/setup.js.map +1 -1
- package/dist/stripe.js +2 -2
- package/dist/stripe.js.map +1 -1
- package/dist/ui/errors.js +17 -17
- package/dist/ui/errors.js.map +1 -1
- package/dist/ui/prompts.js +1 -1
- package/dist/ui/prompts.js.map +1 -1
- package/landing/public/.well-known/ai-plugin.json +6 -6
- package/landing/public/.well-known/openapi.json +295 -0
- package/landing/public/sitemap.xml +15 -0
- package/landing/src/app/api/mou/sign/route.ts +166 -168
- package/landing/src/app/founding-backer/success/page.tsx +115 -0
- package/landing/src/app/layout.tsx +35 -0
- package/landing/src/app/mou/coaccept/page.tsx +13 -13
- package/landing/src/app/page.tsx +3 -4
- package/package.json +1 -1
- package/src/cli/commands/doctor.ts +49 -36
- package/src/cli/commands/setup.ts +2 -2
- package/src/stripe.ts +2 -2
- package/src/ui/errors.ts +17 -17
- package/src/ui/prompts.ts +1 -1
|
@@ -1,9 +1,7 @@
|
|
|
1
1
|
import { NextRequest, NextResponse } from "next/server";
|
|
2
|
-
import { generatePdfFromHtml } from "@/lib/pdf";
|
|
3
2
|
|
|
4
3
|
// MOU functions deployed to adventurous-avocet-799
|
|
5
4
|
const CONVEX_URL = "https://adventurous-avocet-799.convex.cloud";
|
|
6
|
-
const RESEND_API_KEY = process.env.RESEND_API_KEY;
|
|
7
5
|
|
|
8
6
|
interface PartnerConfig {
|
|
9
7
|
name: string;
|
|
@@ -20,154 +18,186 @@ const partnerConfig: Record<string, PartnerConfig> = {
|
|
|
20
18
|
function generateMouHtml(partner: PartnerConfig, signerName: string, signerTitle: string, signatureDataUrl: string, signedDate: string): string {
|
|
21
19
|
const isAdvisory = partner.type === "advisory";
|
|
22
20
|
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
<
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
<
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
</div>
|
|
124
|
-
|
|
125
|
-
<div style="margin-top: 30px; padding: 20px; background: #f0fdf4; border-radius: 8px; text-align: center;">
|
|
126
|
-
<p style="color: #166534; margin: 0;">✓ This document has been digitally signed by both parties</p>
|
|
127
|
-
</div>
|
|
128
|
-
</div>
|
|
129
|
-
</body>
|
|
130
|
-
</html>
|
|
131
|
-
`;
|
|
21
|
+
return `<!DOCTYPE html>
|
|
22
|
+
<html>
|
|
23
|
+
<body style="font-family: -apple-system, BlinkMacSystemFont, sans-serif; max-width: 700px; margin: 0 auto; padding: 40px; background: #fafafa;">
|
|
24
|
+
<div style="background: white; border-radius: 16px; padding: 40px; border: 1px solid #e5e5e5;">
|
|
25
|
+
<div style="text-align: center; margin-bottom: 30px;">
|
|
26
|
+
<div style="font-size: 36px; font-weight: bold; color: #dc2626;">APIClaw</div>
|
|
27
|
+
<h1 style="margin: 10px 0; color: #1a1a1a;">APIClaw x ${partner.name}</h1>
|
|
28
|
+
<p style="color: #dc2626; font-weight: 600;">SIGNED MEMORANDUM OF UNDERSTANDING</p>
|
|
29
|
+
<p style="color: #737373;">${isAdvisory ? 'Advisory Partnership - ' : ''}Signed on ${signedDate}</p>
|
|
30
|
+
</div>
|
|
31
|
+
|
|
32
|
+
<div style="border-top: 2px solid #dc2626; padding-top: 30px;">
|
|
33
|
+
<h2 style="color: #dc2626;">1. Parties</h2>
|
|
34
|
+
<p><strong>APIClaw</strong> (NordSym AB, org.nr 559535-5768), Gustav Hemmingsson, CEO</p>
|
|
35
|
+
<p><strong>${partner.name}</strong>, ${signerName}, ${signerTitle}</p>
|
|
36
|
+
|
|
37
|
+
${isAdvisory ? `
|
|
38
|
+
<h2 style="color: #dc2626;">2. Purpose</h2>
|
|
39
|
+
<ul>
|
|
40
|
+
<li>Strategic advisory partnership for APIClaw's growth</li>
|
|
41
|
+
<li>Network access and key introductions</li>
|
|
42
|
+
<li>Business development support</li>
|
|
43
|
+
<li>Long-term, trust-based collaboration</li>
|
|
44
|
+
</ul>
|
|
45
|
+
|
|
46
|
+
<h2 style="color: #dc2626;">3. ${partner.name} Provides</h2>
|
|
47
|
+
<ul>
|
|
48
|
+
<li><strong>Strategic Advisory:</strong> Business strategy and growth guidance</li>
|
|
49
|
+
<li><strong>Network & Introductions:</strong> Access to customers, partners, investors</li>
|
|
50
|
+
<li><strong>Business Development:</strong> Deal structuring and negotiations</li>
|
|
51
|
+
</ul>
|
|
52
|
+
|
|
53
|
+
<h2 style="color: #dc2626;">4. APIClaw / NordSym Provides</h2>
|
|
54
|
+
<ul>
|
|
55
|
+
<li><strong>Product Access:</strong> Full platform access</li>
|
|
56
|
+
<li><strong>Revenue Share:</strong> Success fee on referred deals</li>
|
|
57
|
+
<li><strong>Collaboration:</strong> Open communication</li>
|
|
58
|
+
</ul>
|
|
59
|
+
|
|
60
|
+
<h2 style="color: #dc2626;">5. Terms</h2>
|
|
61
|
+
<ul>
|
|
62
|
+
<li>Non-exclusive partnership</li>
|
|
63
|
+
<li>Good faith collaboration</li>
|
|
64
|
+
<li>Confidential business information</li>
|
|
65
|
+
<li>30-day notice for termination</li>
|
|
66
|
+
</ul>
|
|
67
|
+
` : `
|
|
68
|
+
<h2 style="color: #dc2626;">2. Purpose</h2>
|
|
69
|
+
<ul>
|
|
70
|
+
<li>Putting ${partner.name}'s APIs in front of AI Agents</li>
|
|
71
|
+
<li>Providing ${partner.name} with featured provider status and attribution</li>
|
|
72
|
+
<li>Exploring co-marketing opportunities</li>
|
|
73
|
+
<li>Enabling AI agents to discover and use ${partner.name} APIs</li>
|
|
74
|
+
</ul>
|
|
75
|
+
|
|
76
|
+
<h2 style="color: #dc2626;">3. Proposed Collaboration</h2>
|
|
77
|
+
<p><strong>Phase 1:</strong> Discovery Integration</p>
|
|
78
|
+
<p><strong>Phase 2:</strong> Direct Call Pilot</p>
|
|
79
|
+
<p><strong>Phase 3:</strong> Scale & Co-Marketing</p>
|
|
80
|
+
|
|
81
|
+
<h2 style="color: #dc2626;">4. Non-Binding Intent</h2>
|
|
82
|
+
<p>This MOU is not legally binding. It serves as a foundation for further discussions.</p>
|
|
83
|
+
|
|
84
|
+
<h2 style="color: #dc2626;">5. Confidentiality</h2>
|
|
85
|
+
<p>Both parties agree to treat shared business information as confidential.</p>
|
|
86
|
+
|
|
87
|
+
<h2 style="color: #dc2626;">6. Next Steps</h2>
|
|
88
|
+
<ul>
|
|
89
|
+
<li>Set up Telegram group for technical coordination</li>
|
|
90
|
+
<li>Agree on pilot APIs and integration approach</li>
|
|
91
|
+
<li>Launch pilot, iterate based on learnings</li>
|
|
92
|
+
</ul>
|
|
93
|
+
`}
|
|
94
|
+
</div>
|
|
95
|
+
|
|
96
|
+
<div style="border-top: 2px solid #e5e5e5; margin-top: 30px; padding-top: 30px;">
|
|
97
|
+
<h2 style="color: #dc2626;">Signatures</h2>
|
|
98
|
+
<table width="100%">
|
|
99
|
+
<tr>
|
|
100
|
+
<td style="width: 50%; vertical-align: top;">
|
|
101
|
+
<p style="color: #737373; font-size: 12px;">APICLAW / NORDSYM AB</p>
|
|
102
|
+
<p style="font-family: 'Brush Script MT', cursive; font-size: 24px;">Gustav Hemmingsson</p>
|
|
103
|
+
<p><strong>Gustav Hemmingsson</strong><br>CEO, NordSym AB<br>March 5, 2026</p>
|
|
104
|
+
</td>
|
|
105
|
+
<td style="width: 50%; vertical-align: top;">
|
|
106
|
+
<p style="color: #737373; font-size: 12px;">${partner.name.toUpperCase()}</p>
|
|
107
|
+
<img src="${signatureDataUrl}" style="max-width: 200px; max-height: 80px;" alt="Signature"/>
|
|
108
|
+
<p><strong>${signerName}</strong><br>${signerTitle}<br>${signedDate}</p>
|
|
109
|
+
</td>
|
|
110
|
+
</tr>
|
|
111
|
+
</table>
|
|
112
|
+
</div>
|
|
113
|
+
|
|
114
|
+
<div style="margin-top: 30px; padding: 20px; background: #f0fdf4; border-radius: 8px; text-align: center;">
|
|
115
|
+
<p style="color: #166534; margin: 0;">This document has been digitally signed by both parties</p>
|
|
116
|
+
</div>
|
|
117
|
+
</div>
|
|
118
|
+
</body>
|
|
119
|
+
</html>`;
|
|
120
|
+
}
|
|
132
121
|
|
|
133
|
-
|
|
122
|
+
function generateEmailBody(partner: PartnerConfig, signerName: string, signerTitle: string, signedDate: string): string {
|
|
123
|
+
return `<!DOCTYPE html>
|
|
124
|
+
<html>
|
|
125
|
+
<body style="margin: 0; padding: 40px; background: #f5f5f5; font-family: -apple-system, BlinkMacSystemFont, sans-serif;">
|
|
126
|
+
<div style="max-width: 500px; margin: 0 auto; background: white; border-radius: 16px; overflow: hidden; box-shadow: 0 2px 8px rgba(0,0,0,0.1);">
|
|
127
|
+
<div style="background: #dc2626; color: white; padding: 24px; text-align: center;">
|
|
128
|
+
<div style="font-size: 28px; font-weight: bold;">APIClaw</div>
|
|
129
|
+
<h1 style="margin: 8px 0 0; font-size: 20px;">APIClaw x ${partner.name}</h1>
|
|
130
|
+
</div>
|
|
131
|
+
<div style="padding: 32px;">
|
|
132
|
+
<p style="color: #166534; background: #f0fdf4; padding: 12px 16px; border-radius: 8px; margin: 0 0 24px;">
|
|
133
|
+
✓ MOU has been signed successfully
|
|
134
|
+
</p>
|
|
135
|
+
<table style="width: 100%; border-collapse: collapse;">
|
|
136
|
+
<tr>
|
|
137
|
+
<td style="padding: 8px 0; color: #737373;">Signed by</td>
|
|
138
|
+
<td style="padding: 8px 0; font-weight: 600;">${signerName}, ${signerTitle}</td>
|
|
139
|
+
</tr>
|
|
140
|
+
<tr>
|
|
141
|
+
<td style="padding: 8px 0; color: #737373;">Date</td>
|
|
142
|
+
<td style="padding: 8px 0; font-weight: 600;">${signedDate}</td>
|
|
143
|
+
</tr>
|
|
144
|
+
<tr>
|
|
145
|
+
<td style="padding: 8px 0; color: #737373;">Document</td>
|
|
146
|
+
<td style="padding: 8px 0; font-weight: 600;">Attached as HTML file</td>
|
|
147
|
+
</tr>
|
|
148
|
+
</table>
|
|
149
|
+
</div>
|
|
150
|
+
<div style="padding: 16px 32px; background: #fafafa; border-top: 1px solid #e5e5e5; text-align: center;">
|
|
151
|
+
<p style="margin: 0; font-size: 12px; color: #737373;">APIClaw - The API Layer for AI Agents</p>
|
|
152
|
+
</div>
|
|
153
|
+
</div>
|
|
154
|
+
</body>
|
|
155
|
+
</html>`;
|
|
134
156
|
}
|
|
135
157
|
|
|
136
|
-
async function
|
|
158
|
+
async function sendEmailWithAttachment(
|
|
137
159
|
to: string,
|
|
138
160
|
subject: string,
|
|
139
|
-
|
|
140
|
-
|
|
161
|
+
partner: PartnerConfig,
|
|
162
|
+
signerName: string,
|
|
163
|
+
signerTitle: string,
|
|
164
|
+
signedDate: string,
|
|
165
|
+
attachmentHtml: string,
|
|
141
166
|
filename: string
|
|
142
167
|
): Promise<boolean> {
|
|
143
168
|
try {
|
|
144
|
-
|
|
169
|
+
// Use TextEncoder for proper UTF-8 base64 encoding
|
|
170
|
+
const encoder = new TextEncoder();
|
|
171
|
+
const uint8Array = encoder.encode(attachmentHtml);
|
|
172
|
+
let binary = '';
|
|
173
|
+
uint8Array.forEach(byte => binary += String.fromCharCode(byte));
|
|
174
|
+
const base64Data = btoa(binary);
|
|
175
|
+
|
|
176
|
+
const emailBody = generateEmailBody(partner, signerName, signerTitle, signedDate);
|
|
177
|
+
|
|
178
|
+
const response = await fetch("https://nordsym.app.n8n.cloud/webhook/symbot-gmail", {
|
|
145
179
|
method: "POST",
|
|
146
|
-
headers: {
|
|
147
|
-
"Authorization": `Bearer ${RESEND_API_KEY}`,
|
|
148
|
-
"Content-Type": "application/json",
|
|
149
|
-
},
|
|
180
|
+
headers: { "Content-Type": "application/json" },
|
|
150
181
|
body: JSON.stringify({
|
|
151
|
-
|
|
152
|
-
to
|
|
182
|
+
action: "send",
|
|
183
|
+
to,
|
|
153
184
|
subject,
|
|
154
|
-
|
|
185
|
+
message: emailBody,
|
|
155
186
|
attachments: [
|
|
156
187
|
{
|
|
157
|
-
filename,
|
|
158
|
-
|
|
188
|
+
filename: filename,
|
|
189
|
+
data: base64Data,
|
|
159
190
|
},
|
|
160
191
|
],
|
|
161
192
|
}),
|
|
162
193
|
});
|
|
163
194
|
|
|
164
195
|
if (!response.ok) {
|
|
165
|
-
|
|
166
|
-
console.error(`Failed to send email to ${to}:`, error);
|
|
196
|
+
console.error(`Failed to send email to ${to}`);
|
|
167
197
|
return false;
|
|
168
198
|
}
|
|
169
199
|
|
|
170
|
-
console.log(
|
|
200
|
+
console.log(`Email sent to ${to}`);
|
|
171
201
|
return true;
|
|
172
202
|
} catch (error) {
|
|
173
203
|
console.error(`Error sending email to ${to}:`, error);
|
|
@@ -195,11 +225,10 @@ export async function POST(request: NextRequest) {
|
|
|
195
225
|
);
|
|
196
226
|
}
|
|
197
227
|
|
|
198
|
-
// Get client IP
|
|
199
228
|
const forwardedFor = request.headers.get("x-forwarded-for");
|
|
200
229
|
const signerIp = forwardedFor?.split(",")[0] || "unknown";
|
|
201
230
|
|
|
202
|
-
//
|
|
231
|
+
// Check if MOU exists
|
|
203
232
|
const queryResponse = await fetch(`${CONVEX_URL}/api/query`, {
|
|
204
233
|
method: "POST",
|
|
205
234
|
headers: { "Content-Type": "application/json" },
|
|
@@ -212,7 +241,7 @@ export async function POST(request: NextRequest) {
|
|
|
212
241
|
const queryResult = await queryResponse.json();
|
|
213
242
|
const existingMOU = queryResult.value;
|
|
214
243
|
|
|
215
|
-
//
|
|
244
|
+
// Create MOU if not exists
|
|
216
245
|
if (!existingMOU) {
|
|
217
246
|
await fetch(`${CONVEX_URL}/api/mutation`, {
|
|
218
247
|
method: "POST",
|
|
@@ -263,45 +292,14 @@ export async function POST(request: NextRequest) {
|
|
|
263
292
|
|
|
264
293
|
const mouHtml = generateMouHtml(partner, signerName, signerTitle, signatureDataUrl, signedDate);
|
|
265
294
|
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
try {
|
|
269
|
-
pdfBuffer = await generatePdfFromHtml(mouHtml);
|
|
270
|
-
console.log(`✅ PDF generated: ${pdfBuffer.length} bytes`);
|
|
271
|
-
} catch (pdfError) {
|
|
272
|
-
console.error("PDF generation failed:", pdfError);
|
|
273
|
-
// Continue without PDF - send HTML email as fallback
|
|
274
|
-
}
|
|
275
|
-
|
|
276
|
-
const filename = `APIClaw_MOU_${partner.name.replace(/\s+/g, '_')}_${new Date().toISOString().split('T')[0]}.pdf`;
|
|
277
|
-
const emailSubject = `🦞 Signed MOU: APIClaw × ${partner.name}`;
|
|
278
|
-
const emailBody = `
|
|
279
|
-
<p>The MOU between APIClaw and ${partner.name} has been signed.</p>
|
|
280
|
-
<p><strong>Signed by:</strong> ${signerName}, ${signerTitle}</p>
|
|
281
|
-
<p><strong>Date:</strong> ${signedDate}</p>
|
|
282
|
-
<p>The signed document is attached as a PDF.</p>
|
|
283
|
-
`;
|
|
295
|
+
const filename = `APIClaw_MOU_${partner.name.replace(/\s+/g, '_')}_${new Date().toISOString().split('T')[0]}.html`;
|
|
296
|
+
const emailSubject = `Signed MOU: APIClaw x ${partner.name}`;
|
|
284
297
|
|
|
285
298
|
// Send to both parties
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
]);
|
|
291
|
-
} else {
|
|
292
|
-
// Fallback: send HTML email without PDF
|
|
293
|
-
console.log("Sending HTML fallback emails...");
|
|
294
|
-
await fetch("https://nordsym.app.n8n.cloud/webhook/symbot-gmail", {
|
|
295
|
-
method: "POST",
|
|
296
|
-
headers: { "Content-Type": "application/json" },
|
|
297
|
-
body: JSON.stringify({
|
|
298
|
-
action: "send",
|
|
299
|
-
to: "gustav@nordsym.com",
|
|
300
|
-
subject: emailSubject,
|
|
301
|
-
message: mouHtml,
|
|
302
|
-
}),
|
|
303
|
-
});
|
|
304
|
-
}
|
|
299
|
+
await Promise.all([
|
|
300
|
+
sendEmailWithAttachment("gustav@nordsym.com", emailSubject, partner, signerName, signerTitle, signedDate, mouHtml, filename),
|
|
301
|
+
sendEmailWithAttachment(partner.email, emailSubject, partner, signerName, signerTitle, signedDate, mouHtml, filename),
|
|
302
|
+
]);
|
|
305
303
|
|
|
306
304
|
return NextResponse.json({ success: true });
|
|
307
305
|
} catch (error) {
|
|
@@ -0,0 +1,115 @@
|
|
|
1
|
+
import Link from "next/link";
|
|
2
|
+
import { CheckCircle2, ArrowRight, Sparkles, ShieldCheck, Rocket } from "lucide-react";
|
|
3
|
+
|
|
4
|
+
const FOUNDING_BACKER_PAYMENT_LINK = "https://buy.stripe.com/fZu00l5084em8SU6X6cMM0u";
|
|
5
|
+
|
|
6
|
+
export const metadata = {
|
|
7
|
+
title: "Founding Backer Confirmed | APIClaw",
|
|
8
|
+
description: "Your Founding Backer access is active. Welcome to APIClaw.",
|
|
9
|
+
};
|
|
10
|
+
|
|
11
|
+
type SuccessPageProps = {
|
|
12
|
+
searchParams?: {
|
|
13
|
+
session_id?: string;
|
|
14
|
+
};
|
|
15
|
+
};
|
|
16
|
+
|
|
17
|
+
export default function FoundingBackerSuccessPage({ searchParams }: SuccessPageProps) {
|
|
18
|
+
const sessionId = searchParams?.session_id;
|
|
19
|
+
|
|
20
|
+
return (
|
|
21
|
+
<main className="min-h-screen bg-[#0a0a0a] text-zinc-100">
|
|
22
|
+
<div className="pointer-events-none absolute inset-0 overflow-hidden">
|
|
23
|
+
<div className="absolute left-1/2 top-[-240px] h-[520px] w-[520px] -translate-x-1/2 rounded-full bg-red-500/15 blur-3xl" />
|
|
24
|
+
<div className="absolute bottom-[-220px] right-[-120px] h-[420px] w-[420px] rounded-full bg-red-400/10 blur-3xl" />
|
|
25
|
+
</div>
|
|
26
|
+
|
|
27
|
+
<div className="relative mx-auto flex w-full max-w-5xl flex-col gap-10 px-6 py-14 md:px-10 md:py-20">
|
|
28
|
+
<section className="rounded-3xl border border-red-500/30 bg-zinc-950/80 p-8 shadow-[0_0_90px_rgba(239,68,68,0.14)] backdrop-blur md:p-10">
|
|
29
|
+
<div className="mb-6 inline-flex items-center gap-2 rounded-full border border-red-500/40 bg-red-500/10 px-4 py-2 text-sm font-semibold text-red-300">
|
|
30
|
+
<Sparkles className="h-4 w-4" />
|
|
31
|
+
Founding Backer Confirmed
|
|
32
|
+
</div>
|
|
33
|
+
|
|
34
|
+
<h1 className="text-balance text-4xl font-black tracking-tight text-white md:text-5xl">
|
|
35
|
+
You are in.
|
|
36
|
+
</h1>
|
|
37
|
+
<p className="mt-4 max-w-2xl text-pretty text-lg text-zinc-300">
|
|
38
|
+
Thank you for backing APIClaw early. Your Founding Backer access is active, including free API usage through December 31, 2026.
|
|
39
|
+
</p>
|
|
40
|
+
|
|
41
|
+
<div className="mt-8 grid gap-4 sm:grid-cols-3">
|
|
42
|
+
<div className="rounded-2xl border border-zinc-800 bg-zinc-900/70 p-4">
|
|
43
|
+
<div className="mb-2 inline-flex rounded-lg bg-red-500/15 p-2 text-red-300">
|
|
44
|
+
<CheckCircle2 className="h-4 w-4" />
|
|
45
|
+
</div>
|
|
46
|
+
<p className="text-sm font-semibold text-zinc-100">Status</p>
|
|
47
|
+
<p className="mt-1 text-sm text-zinc-400">Payment completed</p>
|
|
48
|
+
</div>
|
|
49
|
+
<div className="rounded-2xl border border-zinc-800 bg-zinc-900/70 p-4">
|
|
50
|
+
<div className="mb-2 inline-flex rounded-lg bg-red-500/15 p-2 text-red-300">
|
|
51
|
+
<ShieldCheck className="h-4 w-4" />
|
|
52
|
+
</div>
|
|
53
|
+
<p className="text-sm font-semibold text-zinc-100">Access window</p>
|
|
54
|
+
<p className="mt-1 text-sm text-zinc-400">Free usage until 2026-12-31</p>
|
|
55
|
+
</div>
|
|
56
|
+
<div className="rounded-2xl border border-zinc-800 bg-zinc-900/70 p-4">
|
|
57
|
+
<div className="mb-2 inline-flex rounded-lg bg-red-500/15 p-2 text-red-300">
|
|
58
|
+
<Rocket className="h-4 w-4" />
|
|
59
|
+
</div>
|
|
60
|
+
<p className="text-sm font-semibold text-zinc-100">Next step</p>
|
|
61
|
+
<p className="mt-1 text-sm text-zinc-400">Open workspace and start building</p>
|
|
62
|
+
</div>
|
|
63
|
+
</div>
|
|
64
|
+
|
|
65
|
+
{sessionId ? (
|
|
66
|
+
<p className="mt-6 font-mono text-xs text-zinc-500">Session: {sessionId}</p>
|
|
67
|
+
) : null}
|
|
68
|
+
|
|
69
|
+
<div className="mt-8 flex flex-col gap-3 sm:flex-row">
|
|
70
|
+
<Link
|
|
71
|
+
href="/workspace"
|
|
72
|
+
className="inline-flex items-center justify-center gap-2 rounded-xl bg-red-500 px-5 py-3 text-sm font-bold text-white transition hover:bg-red-400"
|
|
73
|
+
>
|
|
74
|
+
Open APIClaw Workspace
|
|
75
|
+
<ArrowRight className="h-4 w-4" />
|
|
76
|
+
</Link>
|
|
77
|
+
<Link
|
|
78
|
+
href="/docs"
|
|
79
|
+
className="inline-flex items-center justify-center gap-2 rounded-xl border border-zinc-700 bg-zinc-900 px-5 py-3 text-sm font-semibold text-zinc-200 transition hover:border-zinc-500 hover:bg-zinc-800"
|
|
80
|
+
>
|
|
81
|
+
Setup Guides
|
|
82
|
+
</Link>
|
|
83
|
+
<a
|
|
84
|
+
href={FOUNDING_BACKER_PAYMENT_LINK}
|
|
85
|
+
target="_blank"
|
|
86
|
+
rel="noreferrer"
|
|
87
|
+
className="inline-flex items-center justify-center gap-2 rounded-xl border border-red-500/50 bg-red-500/10 px-5 py-3 text-sm font-semibold text-red-200 transition hover:bg-red-500/20"
|
|
88
|
+
>
|
|
89
|
+
Founding Backer Link
|
|
90
|
+
</a>
|
|
91
|
+
</div>
|
|
92
|
+
</section>
|
|
93
|
+
|
|
94
|
+
<section className="terminal">
|
|
95
|
+
<div className="terminal-header">
|
|
96
|
+
<span className="terminal-dot terminal-dot-red" />
|
|
97
|
+
<span className="terminal-dot terminal-dot-yellow" />
|
|
98
|
+
<span className="terminal-dot terminal-dot-green" />
|
|
99
|
+
<span className="terminal-title">next-steps.sh</span>
|
|
100
|
+
</div>
|
|
101
|
+
<div className="terminal-body">
|
|
102
|
+
<p className="terminal-command">
|
|
103
|
+
<span className="terminal-prompt">$</span> npx @nordsym/apiclaw mcp-install
|
|
104
|
+
</p>
|
|
105
|
+
<p className="terminal-output mt-2">Auto-configures supported MCP clients</p>
|
|
106
|
+
<p className="terminal-command mt-4">
|
|
107
|
+
<span className="terminal-prompt">$</span> codex mcp add apiclaw -- node /path/to/apiclaw/dist/index.js
|
|
108
|
+
</p>
|
|
109
|
+
<p className="terminal-output mt-2">Recommended for local Codex integration</p>
|
|
110
|
+
</div>
|
|
111
|
+
</section>
|
|
112
|
+
</div>
|
|
113
|
+
</main>
|
|
114
|
+
);
|
|
115
|
+
}
|
|
@@ -43,6 +43,37 @@ export const metadata: Metadata = {
|
|
|
43
43
|
robots: "index, follow",
|
|
44
44
|
};
|
|
45
45
|
|
|
46
|
+
// Schema.org JSON-LD
|
|
47
|
+
const schemaOrg = {
|
|
48
|
+
"@context": "https://schema.org",
|
|
49
|
+
"@graph": [
|
|
50
|
+
{
|
|
51
|
+
"@type": "WebSite",
|
|
52
|
+
"name": "APIClaw",
|
|
53
|
+
"url": "https://apiclaw.nordsym.com",
|
|
54
|
+
"description": "The API layer for AI agents. Discover and call APIs via MCP with structured data and ranked results."
|
|
55
|
+
},
|
|
56
|
+
{
|
|
57
|
+
"@type": "Organization",
|
|
58
|
+
"name": "NordSym AB",
|
|
59
|
+
"url": "https://nordsym.com"
|
|
60
|
+
},
|
|
61
|
+
{
|
|
62
|
+
"@type": "SoftwareApplication",
|
|
63
|
+
"name": "APIClaw",
|
|
64
|
+
"applicationCategory": "DeveloperApplication",
|
|
65
|
+
"operatingSystem": "Web",
|
|
66
|
+
"description": "API discovery and execution layer for AI agents. 22,000+ APIs indexed. MCP native. Direct Call providers.",
|
|
67
|
+
"offers": {
|
|
68
|
+
"@type": "Offer",
|
|
69
|
+
"price": "0",
|
|
70
|
+
"priceCurrency": "USD",
|
|
71
|
+
"description": "Free tier available"
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
]
|
|
75
|
+
};
|
|
76
|
+
|
|
46
77
|
export default function RootLayout({
|
|
47
78
|
children,
|
|
48
79
|
}: Readonly<{
|
|
@@ -57,6 +88,10 @@ export default function RootLayout({
|
|
|
57
88
|
<meta name="theme-color" content="#ef4444" />
|
|
58
89
|
<meta name="apple-mobile-web-app-capable" content="yes" />
|
|
59
90
|
<meta name="apple-mobile-web-app-status-bar-style" content="black-translucent" />
|
|
91
|
+
<script
|
|
92
|
+
type="application/ld+json"
|
|
93
|
+
dangerouslySetInnerHTML={{ __html: JSON.stringify(schemaOrg) }}
|
|
94
|
+
/>
|
|
60
95
|
</head>
|
|
61
96
|
<body className="antialiased bg-background text-text-primary">
|
|
62
97
|
{children}
|
|
@@ -116,11 +116,11 @@ export default function CoAcceptMOU() {
|
|
|
116
116
|
{/* Header */}
|
|
117
117
|
<header className="bg-white border-b border-gray-200 py-8 px-4">
|
|
118
118
|
<div className="max-w-3xl mx-auto text-center">
|
|
119
|
-
<div className="text-
|
|
119
|
+
<div className="text-3xl font-bold text-red-600 mb-4">APIClaw</div>
|
|
120
120
|
<h1 className="text-2xl font-bold text-gray-900">APIClaw × CoAccept</h1>
|
|
121
121
|
<p className="text-gray-600 mt-1">Integration Partnership</p>
|
|
122
122
|
<div className="h-1 w-20 bg-red-600 mx-auto mt-4 rounded-full"></div>
|
|
123
|
-
<p className="mt-4 text-sm text-gray-500">Memorandum of Understanding
|
|
123
|
+
<p className="mt-4 text-sm text-gray-500">Memorandum of Understanding</p>
|
|
124
124
|
</div>
|
|
125
125
|
</header>
|
|
126
126
|
|
|
@@ -136,7 +136,7 @@ export default function CoAcceptMOU() {
|
|
|
136
136
|
</h2>
|
|
137
137
|
<div className="space-y-3 text-gray-600">
|
|
138
138
|
<p><strong className="text-gray-900">APIClaw / NordSym AB</strong> (org.nr 559535-5768), represented by Gustav Hemmingsson, CEO</p>
|
|
139
|
-
<p><strong className="text-gray-900">CoAccept</strong>, represented by Gustav Frändfors
|
|
139
|
+
<p><strong className="text-gray-900">CoAccept</strong>, represented by Gustav Frändfors</p>
|
|
140
140
|
</div>
|
|
141
141
|
</div>
|
|
142
142
|
|
|
@@ -229,15 +229,15 @@ export default function CoAcceptMOU() {
|
|
|
229
229
|
<h2 className="text-lg font-semibold text-red-600 border-b-2 border-gray-100 pb-2 mb-4">
|
|
230
230
|
7. Commercial Terms
|
|
231
231
|
</h2>
|
|
232
|
-
<div className="
|
|
233
|
-
<p
|
|
234
|
-
<
|
|
235
|
-
|
|
236
|
-
<li>
|
|
237
|
-
<li>
|
|
238
|
-
<li>
|
|
232
|
+
<div className="space-y-3 text-gray-600">
|
|
233
|
+
<p>Based on previous discussions:</p>
|
|
234
|
+
<ul className="list-disc pl-6 space-y-2">
|
|
235
|
+
<li><strong className="text-gray-900">Pricing Model:</strong> Flat fee per invoice (not percentage of invoice amount)</li>
|
|
236
|
+
<li><strong className="text-gray-900">Partner Pricing:</strong> Max 6 kr per invoice for CoAccept customers</li>
|
|
237
|
+
<li><strong className="text-gray-900">APIClaw Margin:</strong> 20% of distribution price</li>
|
|
238
|
+
<li><strong className="text-gray-900">Support:</strong> CoAccept owns customer support (your tool, our rails)</li>
|
|
239
239
|
</ul>
|
|
240
|
-
<p className="text-sm mt-2 italic">
|
|
240
|
+
<p className="text-sm mt-2 italic">Final commercial terms to be documented in a separate agreement after pilot validation.</p>
|
|
241
241
|
</div>
|
|
242
242
|
</div>
|
|
243
243
|
|
|
@@ -365,7 +365,7 @@ export default function CoAcceptMOU() {
|
|
|
365
365
|
type="text"
|
|
366
366
|
value={signerName}
|
|
367
367
|
onChange={(e) => setSignerName(e.target.value)}
|
|
368
|
-
placeholder="Gustav Frändfors
|
|
368
|
+
placeholder="Gustav Frändfors"
|
|
369
369
|
className="w-full border border-gray-300 rounded-lg px-3 py-2 outline-none focus:border-red-500"
|
|
370
370
|
/>
|
|
371
371
|
</div>
|
|
@@ -375,7 +375,7 @@ export default function CoAcceptMOU() {
|
|
|
375
375
|
type="text"
|
|
376
376
|
value={signerTitle}
|
|
377
377
|
onChange={(e) => setSignerTitle(e.target.value)}
|
|
378
|
-
placeholder="CEO
|
|
378
|
+
placeholder="CEO, CoAccept"
|
|
379
379
|
className="w-full border border-gray-300 rounded-lg px-3 py-2 outline-none focus:border-red-500"
|
|
380
380
|
/>
|
|
381
381
|
</div>
|