ebade 0.4.1 β 0.4.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/CHANGELOG.md +10 -1
- package/README.md +1 -1
- package/cli/scaffold.js +16 -10
- package/cli/templates/activity-chart.tsx +50 -0
- package/cli/templates/cta-banner.tsx +39 -0
- package/cli/templates/faq-accordion.tsx +53 -0
- package/cli/templates/recent-events.tsx +80 -0
- package/cli/templates/sidebar-navigation.tsx +68 -0
- package/cli/templates/stats-grid.tsx +80 -0
- package/cli/templates/testimonials.tsx +69 -0
- package/package.json +1 -1
- package/packages/mcp-server/README.md +4 -6
- package/packages/mcp-server/package-lock.json +4 -4
- package/packages/mcp-server/package.json +3 -3
- package/www/package.json +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -5,6 +5,15 @@ All notable changes to **ebade** will be documented in this file.
|
|
|
5
5
|
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
|
6
6
|
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
|
7
7
|
|
|
8
|
+
## [0.4.3] - 2025-01-10
|
|
9
|
+
|
|
10
|
+
### Fixed
|
|
11
|
+
- Critical bug where templates were not found when running via `npx` (fix using `import.meta.url`).
|
|
12
|
+
- Added missing component templates for SaaS Dashboard and Landing Pages (`testimonials`, `faq-accordion`, `cta-banner`, `activity-chart`, `stats-grid`, `recent-events`).
|
|
13
|
+
- Updated `tsconfig.json` generation to use `jsx: preserve` and added path aliases (`@/*`).
|
|
14
|
+
- Added slugification for `package.json` names to ensure valid naming conventions.
|
|
15
|
+
- Synced framework versions across all packages.
|
|
16
|
+
|
|
8
17
|
## [0.4.1] - 2025-01-10
|
|
9
18
|
|
|
10
19
|
### Added
|
|
@@ -28,7 +37,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
|
|
28
37
|
### Added
|
|
29
38
|
|
|
30
39
|
- π Initial alpha release of **ebade**
|
|
31
|
-
- MCP Server package (
|
|
40
|
+
- MCP Server package (`ebade-mcp-server`) with 4 tools:
|
|
32
41
|
- `ebade_scaffold` - Create full projects from ebade definitions
|
|
33
42
|
- `ebade_validate` - Validate ebade files against schema
|
|
34
43
|
- `ebade_compile` - Compile single ebade to code
|
package/README.md
CHANGED
package/cli/scaffold.js
CHANGED
|
@@ -14,6 +14,10 @@ import ora from "ora";
|
|
|
14
14
|
import prompts from "prompts";
|
|
15
15
|
import chokidar from "chokidar";
|
|
16
16
|
import { execSync } from "child_process";
|
|
17
|
+
import { fileURLToPath } from "url";
|
|
18
|
+
|
|
19
|
+
const __filename = fileURLToPath(import.meta.url);
|
|
20
|
+
const __dirname = path.dirname(__filename);
|
|
17
21
|
|
|
18
22
|
// ============================================
|
|
19
23
|
// ANSI Renk KodlarΔ± (Terminal Γ§Δ±ktΔ±sΔ± iΓ§in)
|
|
@@ -40,7 +44,7 @@ ${colors.magenta} ββββββ ${colors.cyan}ββββββββ$
|
|
|
40
44
|
${colors.magenta} ββββββββ${colors.cyan}ββββββββ${colors.magenta}βββ βββ${colors.cyan}ββββββββ${colors.magenta}ββββββββ
|
|
41
45
|
${colors.magenta} ββββββββ${colors.cyan}βββββββ ${colors.magenta}βββ βββ${colors.cyan}βββββββ ${colors.magenta}ββββββββ${colors.reset}
|
|
42
46
|
|
|
43
|
-
${colors.dim}β¨ Agent-First Framework ${colors.yellow}v0.4.
|
|
47
|
+
${colors.dim}β¨ Agent-First Framework ${colors.yellow}v0.4.3${colors.reset}
|
|
44
48
|
`;
|
|
45
49
|
|
|
46
50
|
const log = {
|
|
@@ -70,8 +74,8 @@ function parseEbade(ebadePath) {
|
|
|
70
74
|
// ============================================
|
|
71
75
|
function getComponentTemplate(componentName, design) {
|
|
72
76
|
const templatePath = path.join(
|
|
73
|
-
|
|
74
|
-
"
|
|
77
|
+
__dirname,
|
|
78
|
+
"templates",
|
|
75
79
|
`${componentName}.tsx`
|
|
76
80
|
);
|
|
77
81
|
|
|
@@ -252,7 +256,7 @@ function generateDatabaseSchema(data) {
|
|
|
252
256
|
function generatePackageJson(config) {
|
|
253
257
|
return JSON.stringify(
|
|
254
258
|
{
|
|
255
|
-
name: config.name,
|
|
259
|
+
name: config.name.toLowerCase().replace(/[^a-z0-9]/g, "-"),
|
|
256
260
|
version: "0.1.0",
|
|
257
261
|
private: true,
|
|
258
262
|
scripts: {
|
|
@@ -263,10 +267,10 @@ function generatePackageJson(config) {
|
|
|
263
267
|
test: "vitest",
|
|
264
268
|
},
|
|
265
269
|
dependencies: {
|
|
266
|
-
next: "^14.
|
|
267
|
-
react: "^18.
|
|
268
|
-
"react-dom": "^18.
|
|
269
|
-
"lucide-react": "^0.
|
|
270
|
+
next: "^14.2.0",
|
|
271
|
+
react: "^18.3.0",
|
|
272
|
+
"react-dom": "^18.3.0",
|
|
273
|
+
"lucide-react": "^0.400.0",
|
|
270
274
|
clsx: "^2.1.0",
|
|
271
275
|
"tailwind-merge": "^2.2.0",
|
|
272
276
|
"class-variance-authority": "^0.7.0",
|
|
@@ -395,10 +399,12 @@ function generateTsConfig() {
|
|
|
395
399
|
moduleResolution: "node",
|
|
396
400
|
resolveJsonModule: true,
|
|
397
401
|
isolatedModules: true,
|
|
398
|
-
jsx: "
|
|
402
|
+
jsx: "preserve",
|
|
399
403
|
incremental: true,
|
|
400
404
|
plugins: [{ name: "next" }],
|
|
401
|
-
paths: {
|
|
405
|
+
paths: {
|
|
406
|
+
"@/*": ["./*"],
|
|
407
|
+
},
|
|
402
408
|
},
|
|
403
409
|
include: ["next-env.d.ts", "**/*.ts", "**/*.tsx", ".next/types/**/*.ts"],
|
|
404
410
|
exclude: ["node_modules"],
|
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
import React from "react";
|
|
2
|
+
import { cn } from "@/lib/utils";
|
|
3
|
+
|
|
4
|
+
/**
|
|
5
|
+
* π§ Generated via ebade
|
|
6
|
+
* Component: ActivityChart
|
|
7
|
+
*/
|
|
8
|
+
export function ActivityChart() {
|
|
9
|
+
const data = [40, 70, 45, 90, 65, 80, 50, 85, 95, 60, 75, 55];
|
|
10
|
+
|
|
11
|
+
return (
|
|
12
|
+
<div className="p-6 rounded-3xl bg-slate-900 border border-slate-800 shadow-sm">
|
|
13
|
+
<div className="flex items-center justify-between mb-8">
|
|
14
|
+
<div>
|
|
15
|
+
<h3 className="text-lg font-bold text-white">Activity Overview</h3>
|
|
16
|
+
<p className="text-sm text-slate-500">
|
|
17
|
+
System throughput over the last 12 hours
|
|
18
|
+
</p>
|
|
19
|
+
</div>
|
|
20
|
+
<div className="flex gap-2">
|
|
21
|
+
<div className="flex items-center gap-1.5">
|
|
22
|
+
<div className="w-2.5 h-2.5 rounded-full bg-indigo-500"></div>
|
|
23
|
+
<span className="text-xs text-slate-400">Requests</span>
|
|
24
|
+
</div>
|
|
25
|
+
</div>
|
|
26
|
+
</div>
|
|
27
|
+
|
|
28
|
+
<div className="flex items-end justify-between h-48 gap-2 px-2">
|
|
29
|
+
{data.map((val, i) => (
|
|
30
|
+
<div
|
|
31
|
+
key={i}
|
|
32
|
+
className="flex-1 flex flex-col items-center gap-2 group"
|
|
33
|
+
>
|
|
34
|
+
<div
|
|
35
|
+
className="w-full bg-indigo-500/20 rounded-t-lg group-hover:bg-indigo-500/40 transition-all relative"
|
|
36
|
+
style={{ height: `${val}%` }}
|
|
37
|
+
>
|
|
38
|
+
<div className="absolute -top-8 left-1/2 -translate-x-1/2 bg-slate-800 text-white text-[10px] px-2 py-1 rounded opacity-0 group-hover:opacity-100 transition-opacity">
|
|
39
|
+
{val}k
|
|
40
|
+
</div>
|
|
41
|
+
</div>
|
|
42
|
+
<span className="text-[10px] text-slate-600 font-mono">
|
|
43
|
+
H{i + 1}
|
|
44
|
+
</span>
|
|
45
|
+
</div>
|
|
46
|
+
))}
|
|
47
|
+
</div>
|
|
48
|
+
</div>
|
|
49
|
+
);
|
|
50
|
+
}
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
import React from "react";
|
|
2
|
+
import { cn } from "@/lib/utils";
|
|
3
|
+
import { ArrowRight } from "lucide-react";
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* π§ Generated via ebade
|
|
7
|
+
* Component: CtaBanner
|
|
8
|
+
*/
|
|
9
|
+
export function CtaBanner() {
|
|
10
|
+
return (
|
|
11
|
+
<section className="py-24 px-4">
|
|
12
|
+
<div className="max-w-5xl mx-auto p-12 rounded-[2.5rem] bg-gradient-to-br from-indigo-600 to-indigo-700 text-center relative overflow-hidden shadow-2xl">
|
|
13
|
+
<div className="absolute top-0 right-0 -mr-20 -mt-20 w-80 h-80 bg-white/10 rounded-full blur-3xl"></div>
|
|
14
|
+
<div className="absolute bottom-0 left-0 -ml-20 -mb-20 w-60 h-60 bg-black/10 rounded-full blur-3xl"></div>
|
|
15
|
+
|
|
16
|
+
<h2 className="text-3xl md:text-5xl font-bold text-white mb-6 relative z-10">
|
|
17
|
+
Ready to build with Intent?
|
|
18
|
+
</h2>
|
|
19
|
+
<p className="text-indigo-100 text-lg mb-10 max-w-2xl mx-auto relative z-10 italic">
|
|
20
|
+
Join the revolution of Agent-First engineering. Transform your YAML
|
|
21
|
+
into production-ready software in seconds.
|
|
22
|
+
</p>
|
|
23
|
+
|
|
24
|
+
<div className="flex flex-col sm:flex-row gap-4 justify-center items-center relative z-10">
|
|
25
|
+
<button className="px-8 py-4 bg-white text-indigo-600 font-bold rounded-2xl hover:bg-slate-50 transition-all flex items-center gap-2 group shadow-xl">
|
|
26
|
+
Get Started Free
|
|
27
|
+
<ArrowRight
|
|
28
|
+
size={20}
|
|
29
|
+
className="group-hover:translate-x-1 transition-transform"
|
|
30
|
+
/>
|
|
31
|
+
</button>
|
|
32
|
+
<button className="px-8 py-4 bg-transparent text-white border border-white/20 font-semibold rounded-2xl hover:bg-white/10 transition-all">
|
|
33
|
+
Contact Sales
|
|
34
|
+
</button>
|
|
35
|
+
</div>
|
|
36
|
+
</div>
|
|
37
|
+
</section>
|
|
38
|
+
);
|
|
39
|
+
}
|
|
@@ -0,0 +1,53 @@
|
|
|
1
|
+
import React from "react";
|
|
2
|
+
import { cn } from "@/lib/utils";
|
|
3
|
+
import { ChevronDown } from "lucide-react";
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* π§ Generated via ebade
|
|
7
|
+
* Component: FaqAccordion
|
|
8
|
+
*/
|
|
9
|
+
export function FaqAccordion() {
|
|
10
|
+
const faqs = [
|
|
11
|
+
{
|
|
12
|
+
q: "What is ebade?",
|
|
13
|
+
a: "ebade is an Agent-First Framework designed to help AI agents build production-ready applications with deterministic outcomes.",
|
|
14
|
+
},
|
|
15
|
+
{
|
|
16
|
+
q: "How does it reduce tokens?",
|
|
17
|
+
a: "By using YAML-based intent definitions, we provide only the essential context to the model, reducing entropy and token consumption.",
|
|
18
|
+
},
|
|
19
|
+
{
|
|
20
|
+
q: "Is it compatible with Next.js?",
|
|
21
|
+
a: "Yes, ebade scaffolds native Next.js projects using the App Router and Tailwind CSS by default.",
|
|
22
|
+
},
|
|
23
|
+
];
|
|
24
|
+
|
|
25
|
+
return (
|
|
26
|
+
<section className="py-24 bg-slate-950">
|
|
27
|
+
<div className="max-w-3xl mx-auto px-4">
|
|
28
|
+
<h2 className="text-3xl font-bold text-white text-center mb-12">
|
|
29
|
+
Frequently Asked Questions
|
|
30
|
+
</h2>
|
|
31
|
+
<div className="space-y-4">
|
|
32
|
+
{faqs.map((f, i) => (
|
|
33
|
+
<div
|
|
34
|
+
key={i}
|
|
35
|
+
className="group rounded-2xl border border-slate-800 bg-slate-900/30 overflow-hidden transition-all"
|
|
36
|
+
>
|
|
37
|
+
<button className="flex items-center justify-between w-full p-6 text-left text-white hover:bg-white/5 transition-colors">
|
|
38
|
+
<span className="font-medium">{f.q}</span>
|
|
39
|
+
<ChevronDown
|
|
40
|
+
size={20}
|
|
41
|
+
className="text-slate-500 group-focus:rotate-180 transition-transform"
|
|
42
|
+
/>
|
|
43
|
+
</button>
|
|
44
|
+
<div className="p-6 pt-0 text-slate-400 text-sm leading-relaxed border-t border-slate-800/50">
|
|
45
|
+
{f.a}
|
|
46
|
+
</div>
|
|
47
|
+
</div>
|
|
48
|
+
))}
|
|
49
|
+
</div>
|
|
50
|
+
</div>
|
|
51
|
+
</section>
|
|
52
|
+
);
|
|
53
|
+
}
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
import React from "react";
|
|
2
|
+
import { cn } from "@/lib/utils";
|
|
3
|
+
import { CheckCircle2, Clock, Info, ShieldAlert } from "lucide-react";
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* π§ Generated via ebade
|
|
7
|
+
* Component: RecentEvents
|
|
8
|
+
*/
|
|
9
|
+
export function RecentEvents() {
|
|
10
|
+
const events = [
|
|
11
|
+
{
|
|
12
|
+
title: "Deployment Successful",
|
|
13
|
+
time: "2m ago",
|
|
14
|
+
type: "success",
|
|
15
|
+
icon: CheckCircle2,
|
|
16
|
+
desc: "Production environment updated to v1.2.4",
|
|
17
|
+
},
|
|
18
|
+
{
|
|
19
|
+
title: "Security Alert",
|
|
20
|
+
time: "15m ago",
|
|
21
|
+
type: "error",
|
|
22
|
+
icon: ShieldAlert,
|
|
23
|
+
desc: "Anomalous login attempt from unknown IP",
|
|
24
|
+
},
|
|
25
|
+
{
|
|
26
|
+
title: "Backup Completed",
|
|
27
|
+
time: "1h ago",
|
|
28
|
+
type: "info",
|
|
29
|
+
icon: Clock,
|
|
30
|
+
desc: "Global database backup finished successfully",
|
|
31
|
+
},
|
|
32
|
+
{
|
|
33
|
+
title: "New Team Member",
|
|
34
|
+
time: "3h ago",
|
|
35
|
+
type: "info",
|
|
36
|
+
icon: Info,
|
|
37
|
+
desc: "Sarah Chen joined the Engineering team",
|
|
38
|
+
},
|
|
39
|
+
];
|
|
40
|
+
|
|
41
|
+
return (
|
|
42
|
+
<div className="p-6 rounded-3xl bg-slate-900 border border-slate-800">
|
|
43
|
+
<h3 className="text-lg font-bold text-white mb-6">Recent Events</h3>
|
|
44
|
+
<div className="space-y-6">
|
|
45
|
+
{events.map((e, i) => {
|
|
46
|
+
const Icon = e.icon;
|
|
47
|
+
return (
|
|
48
|
+
<div key={i} className="flex gap-4 group">
|
|
49
|
+
<div
|
|
50
|
+
className={cn(
|
|
51
|
+
"p-2 rounded-xl h-fit",
|
|
52
|
+
e.type === "success"
|
|
53
|
+
? "bg-emerald-500/10 text-emerald-500"
|
|
54
|
+
: e.type === "error"
|
|
55
|
+
? "bg-red-500/10 text-red-500"
|
|
56
|
+
: "bg-blue-500/10 text-blue-500"
|
|
57
|
+
)}
|
|
58
|
+
>
|
|
59
|
+
<Icon size={18} />
|
|
60
|
+
</div>
|
|
61
|
+
<div className="flex-1 pb-6 border-b border-slate-800/50 group-last:border-0 group-last:pb-0">
|
|
62
|
+
<div className="flex justify-between mb-1">
|
|
63
|
+
<h4 className="text-sm font-semibold text-slate-200">
|
|
64
|
+
{e.title}
|
|
65
|
+
</h4>
|
|
66
|
+
<span className="text-[10px] text-slate-500 uppercase font-bold tracking-wider">
|
|
67
|
+
{e.time}
|
|
68
|
+
</span>
|
|
69
|
+
</div>
|
|
70
|
+
<p className="text-xs text-slate-500 leading-relaxed">
|
|
71
|
+
{e.desc}
|
|
72
|
+
</p>
|
|
73
|
+
</div>
|
|
74
|
+
</div>
|
|
75
|
+
);
|
|
76
|
+
})}
|
|
77
|
+
</div>
|
|
78
|
+
</div>
|
|
79
|
+
);
|
|
80
|
+
}
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
import React from "react";
|
|
2
|
+
import { cn } from "@/lib/utils";
|
|
3
|
+
import {
|
|
4
|
+
LayoutDashboard,
|
|
5
|
+
BarChart3,
|
|
6
|
+
Users2,
|
|
7
|
+
Settings,
|
|
8
|
+
CreditCard,
|
|
9
|
+
Key,
|
|
10
|
+
} from "lucide-react";
|
|
11
|
+
|
|
12
|
+
/**
|
|
13
|
+
* π§ Generated via ebade
|
|
14
|
+
* Component: SidebarNavigation
|
|
15
|
+
*/
|
|
16
|
+
export function SidebarNavigation() {
|
|
17
|
+
const menuItems = [
|
|
18
|
+
{ label: "Dashboard", icon: LayoutDashboard, active: true },
|
|
19
|
+
{ label: "Analytics", icon: BarChart3 },
|
|
20
|
+
{ label: "Team", icon: Users2 },
|
|
21
|
+
{ label: "Billing", icon: CreditCard },
|
|
22
|
+
{ label: "API Keys", icon: Key },
|
|
23
|
+
{ label: "Settings", icon: Settings },
|
|
24
|
+
];
|
|
25
|
+
|
|
26
|
+
return (
|
|
27
|
+
<div className="w-64 h-full bg-slate-900 border-r border-slate-800 flex flex-col p-6">
|
|
28
|
+
<div className="flex items-center gap-3 mb-12">
|
|
29
|
+
<div className="w-8 h-8 bg-indigo-500 rounded-lg flex items-center justify-center text-white font-bold">
|
|
30
|
+
A
|
|
31
|
+
</div>
|
|
32
|
+
<span className="text-white font-bold tracking-tight">AnalyticsHQ</span>
|
|
33
|
+
</div>
|
|
34
|
+
|
|
35
|
+
<div className="flex-1 space-y-2">
|
|
36
|
+
{menuItems.map((item, i) => {
|
|
37
|
+
const Icon = item.icon;
|
|
38
|
+
return (
|
|
39
|
+
<button
|
|
40
|
+
key={i}
|
|
41
|
+
className={cn(
|
|
42
|
+
"flex items-center gap-3 w-full px-4 py-3 rounded-2xl transition-all",
|
|
43
|
+
item.active
|
|
44
|
+
? "bg-indigo-500 text-white"
|
|
45
|
+
: "text-slate-400 hover:bg-slate-800 hover:text-white"
|
|
46
|
+
)}
|
|
47
|
+
>
|
|
48
|
+
<Icon size={20} />
|
|
49
|
+
<span className="text-sm font-medium">{item.label}</span>
|
|
50
|
+
</button>
|
|
51
|
+
);
|
|
52
|
+
})}
|
|
53
|
+
</div>
|
|
54
|
+
|
|
55
|
+
<div className="mt-auto p-4 rounded-2xl bg-indigo-500/10 border border-indigo-500/20">
|
|
56
|
+
<p className="text-xs text-indigo-300 font-bold mb-1 italic">
|
|
57
|
+
PRO PLAN
|
|
58
|
+
</p>
|
|
59
|
+
<p className="text-[10px] text-indigo-400/70 mb-3">
|
|
60
|
+
Upgrade to Enterprise for unlimited seats.
|
|
61
|
+
</p>
|
|
62
|
+
<div className="w-full bg-slate-800 h-1 rounded-full overflow-hidden">
|
|
63
|
+
<div className="bg-indigo-500 h-full w-[65%]"></div>
|
|
64
|
+
</div>
|
|
65
|
+
</div>
|
|
66
|
+
</div>
|
|
67
|
+
);
|
|
68
|
+
}
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
import React from "react";
|
|
2
|
+
import { cn } from "@/lib/utils";
|
|
3
|
+
import { Users, Zap, Shield, TrendingUp } from "lucide-react";
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* π§ Generated via ebade
|
|
7
|
+
* Component: StatsGrid
|
|
8
|
+
*/
|
|
9
|
+
export function StatsGrid() {
|
|
10
|
+
const stats = [
|
|
11
|
+
{
|
|
12
|
+
label: "Active Users",
|
|
13
|
+
value: "12,402",
|
|
14
|
+
growth: "+12.5%",
|
|
15
|
+
icon: Users,
|
|
16
|
+
color: "text-blue-500",
|
|
17
|
+
bg: "bg-blue-500/10",
|
|
18
|
+
},
|
|
19
|
+
{
|
|
20
|
+
label: "Throughput",
|
|
21
|
+
value: "84.2k",
|
|
22
|
+
growth: "+8.1%",
|
|
23
|
+
icon: Zap,
|
|
24
|
+
color: "text-indigo-500",
|
|
25
|
+
bg: "bg-indigo-500/10",
|
|
26
|
+
},
|
|
27
|
+
{
|
|
28
|
+
label: "Security Score",
|
|
29
|
+
value: "98/100",
|
|
30
|
+
growth: "Stable",
|
|
31
|
+
icon: Shield,
|
|
32
|
+
color: "text-emerald-500",
|
|
33
|
+
bg: "bg-emerald-500/10",
|
|
34
|
+
},
|
|
35
|
+
{
|
|
36
|
+
label: "Revenue",
|
|
37
|
+
value: "$42.1k",
|
|
38
|
+
growth: "+24.3%",
|
|
39
|
+
icon: TrendingUp,
|
|
40
|
+
color: "text-violet-500",
|
|
41
|
+
bg: "bg-violet-500/10",
|
|
42
|
+
},
|
|
43
|
+
];
|
|
44
|
+
|
|
45
|
+
return (
|
|
46
|
+
<div className="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-4 gap-6">
|
|
47
|
+
{stats.map((s, i) => {
|
|
48
|
+
const Icon = s.icon;
|
|
49
|
+
return (
|
|
50
|
+
<div
|
|
51
|
+
key={i}
|
|
52
|
+
className="p-6 rounded-3xl bg-slate-900 border border-slate-800 hover:border-slate-700 transition-colors"
|
|
53
|
+
>
|
|
54
|
+
<div className="flex items-start justify-between mb-4">
|
|
55
|
+
<div className={cn("p-3 rounded-2xl", s.bg)}>
|
|
56
|
+
<Icon size={24} className={s.color} />
|
|
57
|
+
</div>
|
|
58
|
+
<span
|
|
59
|
+
className={cn(
|
|
60
|
+
"text-xs font-bold px-2 py-1 rounded-full",
|
|
61
|
+
s.growth.startsWith("+")
|
|
62
|
+
? "bg-emerald-500/10 text-emerald-500"
|
|
63
|
+
: "bg-slate-800 text-slate-400"
|
|
64
|
+
)}
|
|
65
|
+
>
|
|
66
|
+
{s.growth}
|
|
67
|
+
</span>
|
|
68
|
+
</div>
|
|
69
|
+
<div>
|
|
70
|
+
<p className="text-sm text-slate-500 font-medium mb-1">
|
|
71
|
+
{s.label}
|
|
72
|
+
</p>
|
|
73
|
+
<h4 className="text-2xl font-bold text-white">{s.value}</h4>
|
|
74
|
+
</div>
|
|
75
|
+
</div>
|
|
76
|
+
);
|
|
77
|
+
})}
|
|
78
|
+
</div>
|
|
79
|
+
);
|
|
80
|
+
}
|
|
@@ -0,0 +1,69 @@
|
|
|
1
|
+
import React from "react";
|
|
2
|
+
import { cn } from "@/lib/utils";
|
|
3
|
+
import { Star } from "lucide-react";
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* π§ Generated via ebade
|
|
7
|
+
* Component: Testimonials
|
|
8
|
+
*/
|
|
9
|
+
export function Testimonials() {
|
|
10
|
+
const reviews = [
|
|
11
|
+
{
|
|
12
|
+
name: "Alex Rivera",
|
|
13
|
+
role: "CTO at TechFlow",
|
|
14
|
+
content:
|
|
15
|
+
"ebade changed how we bridge the gap between AI intent and production-ready code. It's a game changer.",
|
|
16
|
+
rating: 5,
|
|
17
|
+
},
|
|
18
|
+
{
|
|
19
|
+
name: "Sarah Chen",
|
|
20
|
+
role: "Lead Developer",
|
|
21
|
+
content:
|
|
22
|
+
"The most efficient way to maintain deterministic outputs with LLMs. Low entropy, high quality.",
|
|
23
|
+
rating: 5,
|
|
24
|
+
},
|
|
25
|
+
{
|
|
26
|
+
name: "Marcus Thorne",
|
|
27
|
+
role: "Product Designer",
|
|
28
|
+
content:
|
|
29
|
+
"Finally, a framework that speaks the language of agents without sacrificing developer experience.",
|
|
30
|
+
rating: 5,
|
|
31
|
+
},
|
|
32
|
+
];
|
|
33
|
+
|
|
34
|
+
return (
|
|
35
|
+
<section className="py-24 bg-slate-950">
|
|
36
|
+
<div className="max-w-7xl mx-auto px-4">
|
|
37
|
+
<div className="text-center mb-16">
|
|
38
|
+
<h2 className="text-3xl md:text-4xl font-bold text-white mb-4">
|
|
39
|
+
Trusted by the Best
|
|
40
|
+
</h2>
|
|
41
|
+
<p className="text-slate-400">
|
|
42
|
+
Join thousands of developers building the future of AI-Native
|
|
43
|
+
software.
|
|
44
|
+
</p>
|
|
45
|
+
</div>
|
|
46
|
+
|
|
47
|
+
<div className="grid grid-cols-1 md:grid-cols-3 gap-8">
|
|
48
|
+
{reviews.map((s, i) => (
|
|
49
|
+
<div
|
|
50
|
+
key={i}
|
|
51
|
+
className="p-8 rounded-3xl bg-slate-900/50 border border-slate-800 hover:border-slate-700 transition-all"
|
|
52
|
+
>
|
|
53
|
+
<div className="flex gap-1 mb-4 text-yellow-500">
|
|
54
|
+
{[...Array(s.rating)].map((_, i) => (
|
|
55
|
+
<Star key={i} size={16} fill="currentColor" />
|
|
56
|
+
))}
|
|
57
|
+
</div>
|
|
58
|
+
<p className="text-slate-300 mb-6 italic">"{s.content}"</p>
|
|
59
|
+
<div>
|
|
60
|
+
<p className="text-white font-semibold">{s.name}</p>
|
|
61
|
+
<p className="text-slate-500 text-sm">{s.role}</p>
|
|
62
|
+
</div>
|
|
63
|
+
</div>
|
|
64
|
+
))}
|
|
65
|
+
</div>
|
|
66
|
+
</div>
|
|
67
|
+
</section>
|
|
68
|
+
);
|
|
69
|
+
}
|
package/package.json
CHANGED
|
@@ -1,19 +1,17 @@
|
|
|
1
|
-
# ebade MCP Server
|
|
1
|
+
# ebade MCP Server π£
|
|
2
2
|
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
This MCP (Model Context Protocol) server allows AI agents like Claude, GPT, and others to use ebade for building web applications.
|
|
3
|
+
Model Context Protocol (MCP) server for the **ebade** Agent-First Framework.
|
|
6
4
|
|
|
7
5
|
## Installation
|
|
8
6
|
|
|
9
7
|
```bash
|
|
10
|
-
|
|
8
|
+
npx -y ebade-mcp-server
|
|
11
9
|
```
|
|
12
10
|
|
|
13
11
|
Or locally:
|
|
14
12
|
|
|
15
13
|
```bash
|
|
16
|
-
npm install
|
|
14
|
+
npm install ebade-mcp-server
|
|
17
15
|
```
|
|
18
16
|
|
|
19
17
|
## Configuration
|
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
{
|
|
2
|
-
"name": "
|
|
3
|
-
"version": "0.1
|
|
2
|
+
"name": "ebade-mcp-server",
|
|
3
|
+
"version": "0.4.1",
|
|
4
4
|
"lockfileVersion": 3,
|
|
5
5
|
"requires": true,
|
|
6
6
|
"packages": {
|
|
7
7
|
"": {
|
|
8
|
-
"name": "
|
|
9
|
-
"version": "0.1
|
|
8
|
+
"name": "ebade-mcp-server",
|
|
9
|
+
"version": "0.4.1",
|
|
10
10
|
"license": "MIT",
|
|
11
11
|
"dependencies": {
|
|
12
12
|
"@modelcontextprotocol/sdk": "^1.25.1",
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
|
-
"name": "
|
|
3
|
-
"version": "0.4.
|
|
4
|
-
"description": "MCP Server for ebade v0.4.
|
|
2
|
+
"name": "ebade-mcp-server",
|
|
3
|
+
"version": "0.4.3",
|
|
4
|
+
"description": "MCP Server for ebade v0.4.3 - The Agent-First Framework",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "dist/index.js",
|
|
7
7
|
"bin": {
|