@jerydam/lumina-sdk 0.1.0

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.
Files changed (152) hide show
  1. package/BUTTON_FIXES.md +59 -0
  2. package/DOCS_INDEX.md +332 -0
  3. package/DOCUMENTATION.md +252 -0
  4. package/DOCUMENTATION_BUILD_SUMMARY.md +376 -0
  5. package/DOCUMENTATION_COMPLETE.md +311 -0
  6. package/FEATURES.md +333 -0
  7. package/Lumina-sdk/src/components/lumina-provider.tsx +46 -0
  8. package/Lumina-sdk/src/components/transaction-confirm.tsx +242 -0
  9. package/Lumina-sdk/src/components/wallet-display.tsx +157 -0
  10. package/Lumina-sdk/src/components/wallet-login.tsx +163 -0
  11. package/Lumina-sdk/src/hooks/use-mobile.ts +19 -0
  12. package/Lumina-sdk/src/hooks/use-toast.ts +191 -0
  13. package/Lumina-sdk/src/index.ts +0 -0
  14. package/Lumina-sdk/src/lib/api.ts +66 -0
  15. package/Lumina-sdk/src/lib/utils.ts +6 -0
  16. package/Lumina-sdk/src/package.json +42 -0
  17. package/Lumina-sdk/src/tsconfig.json +19 -0
  18. package/NEW_FILES_MANIFEST.txt +146 -0
  19. package/README.md +298 -0
  20. package/app/dashboard/analytics/page.tsx +218 -0
  21. package/app/dashboard/api-keys/page.tsx +260 -0
  22. package/app/dashboard/billing/page.tsx +412 -0
  23. package/app/dashboard/integration/page.tsx +185 -0
  24. package/app/dashboard/layout.tsx +18 -0
  25. package/app/dashboard/page.tsx +244 -0
  26. package/app/dashboard/settings/page.tsx +285 -0
  27. package/app/dashboard/users/page.tsx +148 -0
  28. package/app/docs/api/authentication/page.tsx +246 -0
  29. package/app/docs/api/endpoints/page.tsx +397 -0
  30. package/app/docs/api/errors/page.tsx +305 -0
  31. package/app/docs/api/overview/page.tsx +306 -0
  32. package/app/docs/examples/basic-setup/page.tsx +256 -0
  33. package/app/docs/examples/multi-chain/page.tsx +331 -0
  34. package/app/docs/examples/nextjs-full-stack/page.tsx +332 -0
  35. package/app/docs/getting-started/environment-setup/page.tsx +243 -0
  36. package/app/docs/getting-started/installation/page.tsx +187 -0
  37. package/app/docs/getting-started/introduction/page.tsx +178 -0
  38. package/app/docs/getting-started/quick-start/page.tsx +199 -0
  39. package/app/docs/guides/nextjs/page.tsx +358 -0
  40. package/app/docs/guides/react/page.tsx +230 -0
  41. package/app/docs/guides/security/page.tsx +284 -0
  42. package/app/docs/layout.tsx +32 -0
  43. package/app/docs/page.tsx +180 -0
  44. package/app/docs/sdk/lumina-provider/page.tsx +186 -0
  45. package/app/docs/sdk/transaction-confirm/page.tsx +331 -0
  46. package/app/docs/sdk/wallet-display/page.tsx +224 -0
  47. package/app/docs/sdk/wallet-login/page.tsx +207 -0
  48. package/app/docs/troubleshooting/common-issues/page.tsx +301 -0
  49. package/app/docs/troubleshooting/faq/page.tsx +105 -0
  50. package/app/globals.css +125 -0
  51. package/app/invite/[token]/page.tsx +78 -0
  52. package/app/layout.tsx +36 -0
  53. package/app/login/page.tsx +175 -0
  54. package/app/page.tsx +336 -0
  55. package/app/sdk-demo/page.tsx +239 -0
  56. package/components/dashboard-sidebar.tsx +113 -0
  57. package/components/docs/breadcrumb.tsx +51 -0
  58. package/components/docs/callout.tsx +53 -0
  59. package/components/docs/code-block.tsx +77 -0
  60. package/components/docs/docs-sidebar.tsx +214 -0
  61. package/components/docs/table-of-contents.tsx +83 -0
  62. package/components/sdk/lumina-provider.tsx +46 -0
  63. package/components/sdk/transaction-confirm.tsx +242 -0
  64. package/components/sdk/wallet-display.tsx +157 -0
  65. package/components/sdk/wallet-login.tsx +163 -0
  66. package/components/theme-provider.tsx +11 -0
  67. package/components/ui/accordion.tsx +66 -0
  68. package/components/ui/alert-dialog.tsx +157 -0
  69. package/components/ui/alert.tsx +66 -0
  70. package/components/ui/aspect-ratio.tsx +11 -0
  71. package/components/ui/avatar.tsx +53 -0
  72. package/components/ui/badge.tsx +46 -0
  73. package/components/ui/breadcrumb.tsx +109 -0
  74. package/components/ui/button-group.tsx +83 -0
  75. package/components/ui/button.tsx +60 -0
  76. package/components/ui/calendar.tsx +213 -0
  77. package/components/ui/card.tsx +92 -0
  78. package/components/ui/carousel.tsx +241 -0
  79. package/components/ui/chart.tsx +351 -0
  80. package/components/ui/checkbox.tsx +32 -0
  81. package/components/ui/collapsible.tsx +33 -0
  82. package/components/ui/command.tsx +184 -0
  83. package/components/ui/context-menu.tsx +252 -0
  84. package/components/ui/dialog.tsx +143 -0
  85. package/components/ui/drawer.tsx +135 -0
  86. package/components/ui/dropdown-menu.tsx +257 -0
  87. package/components/ui/empty.tsx +104 -0
  88. package/components/ui/field.tsx +244 -0
  89. package/components/ui/form.tsx +167 -0
  90. package/components/ui/hover-card.tsx +44 -0
  91. package/components/ui/input-group.tsx +169 -0
  92. package/components/ui/input-otp.tsx +77 -0
  93. package/components/ui/input.tsx +21 -0
  94. package/components/ui/item.tsx +193 -0
  95. package/components/ui/kbd.tsx +28 -0
  96. package/components/ui/label.tsx +24 -0
  97. package/components/ui/menubar.tsx +276 -0
  98. package/components/ui/navigation-menu.tsx +166 -0
  99. package/components/ui/pagination.tsx +127 -0
  100. package/components/ui/popover.tsx +48 -0
  101. package/components/ui/progress.tsx +31 -0
  102. package/components/ui/radio-group.tsx +45 -0
  103. package/components/ui/resizable.tsx +56 -0
  104. package/components/ui/scroll-area.tsx +58 -0
  105. package/components/ui/select.tsx +185 -0
  106. package/components/ui/separator.tsx +28 -0
  107. package/components/ui/sheet.tsx +139 -0
  108. package/components/ui/sidebar.tsx +726 -0
  109. package/components/ui/skeleton.tsx +13 -0
  110. package/components/ui/slider.tsx +59 -0
  111. package/components/ui/sonner.tsx +25 -0
  112. package/components/ui/spinner.tsx +16 -0
  113. package/components/ui/switch.tsx +29 -0
  114. package/components/ui/table.tsx +116 -0
  115. package/components/ui/tabs.tsx +66 -0
  116. package/components/ui/textarea.tsx +18 -0
  117. package/components/ui/toast.tsx +129 -0
  118. package/components/ui/toaster.tsx +35 -0
  119. package/components/ui/toggle-group.tsx +73 -0
  120. package/components/ui/toggle.tsx +47 -0
  121. package/components/ui/tooltip.tsx +61 -0
  122. package/components/ui/use-mobile.tsx +19 -0
  123. package/components/ui/use-toast.ts +191 -0
  124. package/components.json +21 -0
  125. package/hooks/use-mobile.ts +19 -0
  126. package/hooks/use-toast.ts +191 -0
  127. package/lib/api.ts +66 -0
  128. package/lib/utils.ts +6 -0
  129. package/next-env.d.ts +6 -0
  130. package/next.config.mjs +11 -0
  131. package/package.json +73 -0
  132. package/pnpm-workspace.yaml +5 -0
  133. package/postcss.config.mjs +8 -0
  134. package/public/apple-icon.png +0 -0
  135. package/public/fav.jpeg +0 -0
  136. package/public/fav.png +0 -0
  137. package/public/icon-dark-32x32.png +0 -0
  138. package/public/icon-light-32x32.png +0 -0
  139. package/public/icon.png +0 -0
  140. package/public/icon.svg +26 -0
  141. package/public/logo.jpeg +0 -0
  142. package/public/logo.png +0 -0
  143. package/public/logo2.jpeg +0 -0
  144. package/public/logo2.png +0 -0
  145. package/public/placeholder-logo.png +0 -0
  146. package/public/placeholder-logo.svg +1 -0
  147. package/public/placeholder-user.jpg +0 -0
  148. package/public/placeholder.jpg +0 -0
  149. package/public/placeholder.svg +1 -0
  150. package/styles/globals.css +209 -0
  151. package/tailwind.config.ts +15 -0
  152. package/tsconfig.json +41 -0
@@ -0,0 +1,185 @@
1
+ 'use client'
2
+
3
+ import { Card } from '@/components/ui/card'
4
+ import { Button } from '@/components/ui/button'
5
+ import { Code, Copy, ExternalLink, CheckCircle } from 'lucide-react'
6
+
7
+ export default function IntegrationPage() {
8
+ return (
9
+ <div className="space-y-8">
10
+ {/* Header */}
11
+ <div>
12
+ <h1 className="text-4xl font-bold mb-2">Integration</h1>
13
+ <p className="text-foreground/60">Quick start guides for integrating Lumina into your application</p>
14
+ </div>
15
+
16
+ {/* SDK Installation */}
17
+ <Card className="glassmorphism-dark p-6 border-border">
18
+ <h2 className="text-2xl font-semibold mb-4">Get Started with Lumina SDK</h2>
19
+
20
+ <div className="space-y-6">
21
+ <div>
22
+ <h3 className="text-lg font-semibold mb-3">1. Install SDK</h3>
23
+ <div className="bg-white/5 p-4 rounded-lg font-mono text-sm border border-border/50">
24
+ <div className="flex justify-between items-center">
25
+ <code>npm install @lumina/sdk</code>
26
+ <button className="p-2 hover:bg-white/10 rounded">
27
+ <Copy size={16} />
28
+ </button>
29
+ </div>
30
+ </div>
31
+ </div>
32
+
33
+ <div>
34
+ <h3 className="text-lg font-semibold mb-3">2. Initialize Provider</h3>
35
+ <div className="bg-white/5 p-4 rounded-lg font-mono text-sm border border-border/50 overflow-x-auto">
36
+ <pre>{`import { LuminaProvider } from '@lumina/sdk'
37
+
38
+ export default function App() {
39
+ return (
40
+ <LuminaProvider apiKey="lumina_prod_...">
41
+ <YourApp />
42
+ </LuminaProvider>
43
+ )
44
+ }`}</pre>
45
+ </div>
46
+ </div>
47
+
48
+ <div>
49
+ <h3 className="text-lg font-semibold mb-3">3. Create Wallet</h3>
50
+ <div className="bg-white/5 p-4 rounded-lg font-mono text-sm border border-border/50 overflow-x-auto">
51
+ <pre>{`import { useWallet } from '@lumina/sdk'
52
+
53
+ export function MyComponent() {
54
+ const { createWallet } = useWallet()
55
+
56
+ return (
57
+ <button onClick={() => createWallet()}>
58
+ Create Wallet
59
+ </button>
60
+ )
61
+ }`}</pre>
62
+ </div>
63
+ </div>
64
+ </div>
65
+
66
+ <div className="mt-6 flex gap-3">
67
+ <Button className="bg-emerald-600 hover:bg-emerald-700 gap-2">
68
+ <Code size={18} />
69
+ View Full Docs
70
+ </Button>
71
+ <Button variant="outline" className="gap-2">
72
+ <ExternalLink size={18} />
73
+ GitHub Repository
74
+ </Button>
75
+ </div>
76
+ </Card>
77
+
78
+ {/* SDK Examples */}
79
+ <div className="grid grid-cols-1 md:grid-cols-2 gap-6">
80
+ {[
81
+ {
82
+ title: 'React',
83
+ description: 'Modern React hooks and components',
84
+ status: 'Recommended',
85
+ icon: '⚛️',
86
+ },
87
+ {
88
+ title: 'Next.js',
89
+ description: 'Full-stack integration with server components',
90
+ status: 'Recommended',
91
+ icon: '▲',
92
+ },
93
+ {
94
+ title: 'Vue.js',
95
+ description: 'Vue composables and components',
96
+ status: 'Available',
97
+ icon: '✓',
98
+ },
99
+ {
100
+ title: 'Svelte',
101
+ description: 'Svelte stores and components',
102
+ status: 'Available',
103
+ icon: '◆',
104
+ },
105
+ ].map((sdk, index) => (
106
+ <Card key={index} className="glassmorphism-dark p-6 border-border">
107
+ <div className="flex items-start justify-between mb-4">
108
+ <div>
109
+ <h3 className="text-lg font-semibold">{sdk.title}</h3>
110
+ <p className="text-sm text-foreground/60 mt-1">{sdk.description}</p>
111
+ </div>
112
+ <span className="text-3xl">{sdk.icon}</span>
113
+ </div>
114
+ <div className="flex gap-2">
115
+ <Button size="sm" className="flex-1">Learn More</Button>
116
+ <Button size="sm" variant="outline">View Example</Button>
117
+ </div>
118
+ </Card>
119
+ ))}
120
+ </div>
121
+
122
+ {/* Network Support */}
123
+ <Card className="glassmorphism-dark p-6 border-border">
124
+ <h2 className="text-xl font-semibold mb-6">Supported Networks</h2>
125
+
126
+ <div className="grid grid-cols-1 md:grid-cols-2 gap-4">
127
+ {[
128
+ { name: 'Ethereum', mainnet: true, testnet: true },
129
+ { name: 'Polygon', mainnet: true, testnet: true },
130
+ { name: 'Solana', mainnet: true, testnet: true },
131
+ { name: 'Arbitrum', mainnet: true, testnet: true },
132
+ { name: 'Optimism', mainnet: true, testnet: true },
133
+ { name: 'Base', mainnet: true, testnet: true },
134
+ ].map((network, index) => (
135
+ <div key={index} className="flex items-center justify-between p-4 bg-white/5 rounded-lg border border-border/50">
136
+ <span className="font-medium">{network.name}</span>
137
+ <div className="flex gap-3 text-sm">
138
+ {network.mainnet && <span className="text-emerald-500 flex items-center gap-1"><CheckCircle size={14} /> Mainnet</span>}
139
+ {network.testnet && <span className="text-blue-500 flex items-center gap-1"><CheckCircle size={14} /> Testnet</span>}
140
+ </div>
141
+ </div>
142
+ ))}
143
+ </div>
144
+ </Card>
145
+
146
+ {/* Authentication Methods */}
147
+ <Card className="glassmorphism-dark p-6 border-border">
148
+ <h2 className="text-xl font-semibold mb-4">Authentication Methods</h2>
149
+
150
+ <div className="space-y-4">
151
+ {[
152
+ {
153
+ name: 'Passkeys',
154
+ description: 'Biometric and passkey authentication',
155
+ supported: true,
156
+ },
157
+ {
158
+ name: 'Social Login',
159
+ description: 'Google, GitHub, Discord authentication',
160
+ supported: true,
161
+ },
162
+ {
163
+ name: 'Email/Password',
164
+ description: 'Traditional email and password auth',
165
+ supported: true,
166
+ },
167
+ {
168
+ name: 'Web3 Wallet',
169
+ description: 'MetaMask, WalletConnect integration',
170
+ supported: true,
171
+ },
172
+ ].map((method, index) => (
173
+ <div key={index} className="flex items-center justify-between p-4 bg-white/5 rounded-lg border border-border/50">
174
+ <div>
175
+ <p className="font-medium">{method.name}</p>
176
+ <p className="text-sm text-foreground/60">{method.description}</p>
177
+ </div>
178
+ {method.supported && <CheckCircle className="text-emerald-500" size={24} />}
179
+ </div>
180
+ ))}
181
+ </div>
182
+ </Card>
183
+ </div>
184
+ )
185
+ }
@@ -0,0 +1,18 @@
1
+ import { DashboardSidebar } from '@/components/dashboard-sidebar'
2
+
3
+ export default function DashboardLayout({
4
+ children,
5
+ }: {
6
+ children: React.ReactNode
7
+ }) {
8
+ return (
9
+ <div className="flex h-screen bg-background">
10
+ <DashboardSidebar />
11
+ <main className="flex-1 overflow-auto md:ml-0 pt-16 md:pt-0">
12
+ <div className="p-4 md:p-8">
13
+ {children}
14
+ </div>
15
+ </main>
16
+ </div>
17
+ )
18
+ }
@@ -0,0 +1,244 @@
1
+ 'use client'
2
+
3
+ import { BarChart3, Users, Activity, Zap, Droplets, Loader2, ExternalLink } from 'lucide-react'
4
+ import { Card } from '@/components/ui/card'
5
+ import { useState, useEffect } from 'react'
6
+ import { apiClient } from '@/lib/api'
7
+
8
+ interface DeveloperStats {
9
+ total_wallets: number
10
+ total_accounts: number
11
+ total_ops: number
12
+ total_gas_sponsored_wei: number
13
+ ops_this_month: number
14
+ monthly_limit: number | null
15
+ plan: string
16
+ }
17
+
18
+ interface RecentWallet {
19
+ id: string
20
+ signer_address: string
21
+ oauth_provider: string
22
+ created_at: string
23
+ account_count: number
24
+ }
25
+
26
+ export default function DashboardPage() {
27
+ const [stats, setStats] = useState<DeveloperStats | null>(null)
28
+ const [recentWallets, setRecentWallets] = useState<RecentWallet[]>([])
29
+ const [isLoading, setIsLoading] = useState(true)
30
+
31
+ useEffect(() => {
32
+ const fetchDashboardData = async () => {
33
+ try {
34
+ setIsLoading(true)
35
+ const [statsData, walletsData] = await Promise.all([
36
+ apiClient.dashboard('/v1/developers/stats'),
37
+ apiClient.dashboard('/v1/wallets?limit=5&offset=0') // Just grab the 5 newest
38
+ ])
39
+
40
+ setStats(statsData)
41
+ setRecentWallets(walletsData.wallets || [])
42
+ } catch (error) {
43
+ console.error('Failed to load dashboard data:', error)
44
+ } finally {
45
+ setIsLoading(false)
46
+ }
47
+ }
48
+
49
+ fetchDashboardData()
50
+ }, [])
51
+
52
+ const formatWei = (wei: number | undefined) => {
53
+ if (wei === undefined) return '0.0000'
54
+ return (wei / 1e18).toFixed(4)
55
+ }
56
+
57
+ if (isLoading) {
58
+ return (
59
+ <div className="min-h-[60vh] flex items-center justify-center">
60
+ <Loader2 className="w-8 h-8 animate-spin text-emerald-500" />
61
+ </div>
62
+ )
63
+ }
64
+
65
+ return (
66
+ <div className="space-y-8">
67
+ {/* Header */}
68
+ <div>
69
+ <h1 className="text-4xl font-bold mb-2">Dashboard</h1>
70
+ <p className="text-foreground/60">Welcome back to your Lumina workspace</p>
71
+ </div>
72
+
73
+ {/* Stats Grid */}
74
+ <div className="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-4 gap-4">
75
+ {[
76
+ {
77
+ label: 'Total Wallets',
78
+ value: stats?.total_wallets.toLocaleString() || '0',
79
+ icon: Users,
80
+ color: 'emerald',
81
+ },
82
+ {
83
+ label: 'Smart Accounts',
84
+ value: stats?.total_accounts.toLocaleString() || '0',
85
+ icon: Activity,
86
+ color: 'blue',
87
+ },
88
+ {
89
+ label: 'Total Operations',
90
+ value: stats?.total_ops.toLocaleString() || '0',
91
+ icon: Zap,
92
+ color: 'amber',
93
+ },
94
+ {
95
+ label: 'Gas Sponsored',
96
+ value: `${formatWei(stats?.total_gas_sponsored_wei)} ETH`,
97
+ icon: Droplets,
98
+ color: 'emerald',
99
+ },
100
+ ].map((stat, index) => {
101
+ const Icon = stat.icon
102
+ return (
103
+ <Card key={index} className="glassmorphism-dark p-6 border-border">
104
+ <div className="flex items-start justify-between">
105
+ <div>
106
+ <p className="text-sm text-foreground/60 mb-1">{stat.label}</p>
107
+ <p className="text-3xl font-bold">{stat.value}</p>
108
+ </div>
109
+ <div className={`p-3 rounded-lg bg-${stat.color}-600/10`}>
110
+ <Icon className={`text-${stat.color}-500`} size={24} />
111
+ </div>
112
+ </div>
113
+ </Card>
114
+ )
115
+ })}
116
+ </div>
117
+
118
+ {/* Main Charts Area */}
119
+ <div className="grid grid-cols-1 lg:grid-cols-3 gap-6">
120
+ {/* Activity Chart (Requires a new time-series endpoint in backend to make dynamic) */}
121
+ <Card className="glassmorphism-dark p-6 border-border lg:col-span-2">
122
+ <div className="mb-6 flex justify-between items-start">
123
+ <div>
124
+ <h2 className="text-xl font-semibold mb-1">Monthly Activity</h2>
125
+ <p className="text-sm text-foreground/60">Wallet creation trends (Demo Data)</p>
126
+ </div>
127
+ <BarChart3 className="text-emerald-500" size={24} />
128
+ </div>
129
+
130
+ <div className="space-y-4">
131
+ {[
132
+ { month: 'Jan', wallets: 85, pct: '65%' },
133
+ { month: 'Feb', wallets: 92, pct: '71%' },
134
+ { month: 'Mar', wallets: 78, pct: '59%' },
135
+ { month: 'Apr', wallets: 105, pct: '81%' },
136
+ { month: 'May', wallets: 118, pct: '91%' },
137
+ { month: 'Jun', wallets: 142, pct: '100%' },
138
+ ].map((item, index) => (
139
+ <div key={index} className="flex items-center gap-4">
140
+ <div className="w-12 text-sm font-medium text-foreground/60">{item.month}</div>
141
+ <div className="flex-1">
142
+ <div className="h-8 bg-white/5 rounded-lg overflow-hidden">
143
+ <div
144
+ className="h-full bg-gradient-to-r from-emerald-500 to-emerald-600 transition-all duration-500"
145
+ style={{ width: item.pct }}
146
+ />
147
+ </div>
148
+ </div>
149
+ <div className="text-sm font-medium w-12 text-right">{item.wallets}</div>
150
+ </div>
151
+ ))}
152
+ </div>
153
+ </Card>
154
+
155
+ {/* System & Plan Status */}
156
+ <Card className="glassmorphism-dark p-6 border-border flex flex-col">
157
+ <div>
158
+ <h2 className="text-xl font-semibold mb-4">Current Plan</h2>
159
+ <div className="p-4 bg-emerald-600/10 border border-emerald-600/20 rounded-lg mb-6 text-center">
160
+ <p className="text-sm text-foreground/60 uppercase tracking-wider mb-1">Tier</p>
161
+ <p className="text-2xl font-bold capitalize text-emerald-400">{stats?.plan || 'Free'}</p>
162
+ </div>
163
+ </div>
164
+
165
+ <div className="border-t border-border pt-6 mt-auto">
166
+ <h3 className="text-sm font-semibold mb-3 flex items-center gap-2">
167
+ <div className="w-2 h-2 rounded-full bg-emerald-500 animate-pulse"></div>
168
+ System Health
169
+ </h3>
170
+ <div className="space-y-2">
171
+ <div className="flex justify-between text-sm">
172
+ <span className="text-foreground/60">Paymaster Status</span>
173
+ <span className="font-medium text-emerald-500">Operational</span>
174
+ </div>
175
+ <div className="flex justify-between text-sm">
176
+ <span className="text-foreground/60">Bundler Relay</span>
177
+ <span className="font-medium text-emerald-500">Operational</span>
178
+ </div>
179
+ <div className="flex justify-between text-sm">
180
+ <span className="text-foreground/60">Operations Limit</span>
181
+ <span className="font-medium">
182
+ {stats?.ops_this_month} / {stats?.monthly_limit || '∞'}
183
+ </span>
184
+ </div>
185
+ </div>
186
+ </div>
187
+ </Card>
188
+ </div>
189
+
190
+ {/* Recent Wallets */}
191
+ <Card className="glassmorphism-dark p-6 border-border">
192
+ <div className="mb-6">
193
+ <h2 className="text-xl font-semibold mb-1">Recently Created Wallets</h2>
194
+ <p className="text-sm text-foreground/60">The newest users to join your application</p>
195
+ </div>
196
+
197
+ <div className="overflow-x-auto">
198
+ <table className="w-full text-sm">
199
+ <thead>
200
+ <tr className="border-b border-border bg-white/5">
201
+ <th className="text-left py-3 px-4 text-foreground/60 font-medium rounded-tl-lg">Signer Address</th>
202
+ <th className="text-left py-3 px-4 text-foreground/60 font-medium">Auth Provider</th>
203
+ <th className="text-left py-3 px-4 text-foreground/60 font-medium">Smart Accounts</th>
204
+ <th className="text-left py-3 px-4 text-foreground/60 font-medium">Joined Date</th>
205
+ <th className="text-right py-3 px-4 text-foreground/60 font-medium rounded-tr-lg">Action</th>
206
+ </tr>
207
+ </thead>
208
+ <tbody>
209
+ {recentWallets.length === 0 ? (
210
+ <tr>
211
+ <td colSpan={5} className="py-8 text-center text-foreground/60">
212
+ No wallets created yet.
213
+ </td>
214
+ </tr>
215
+ ) : (
216
+ recentWallets.map((wallet) => (
217
+ <tr key={wallet.id} className="border-b border-border/50 hover:bg-white/5 transition">
218
+ <td className="py-3 px-4">
219
+ <code className="text-xs font-mono">{wallet.signer_address}</code>
220
+ </td>
221
+ <td className="py-3 px-4 capitalize">
222
+ <span className="px-2 py-1 bg-white/10 rounded-full text-xs">
223
+ {wallet.oauth_provider}
224
+ </span>
225
+ </td>
226
+ <td className="py-3 px-4 font-medium">{wallet.account_count}</td>
227
+ <td className="py-3 px-4 text-foreground/60">
228
+ {new Date(wallet.created_at).toLocaleDateString()}
229
+ </td>
230
+ <td className="py-3 px-4 text-right">
231
+ <button className="text-foreground/60 hover:text-emerald-400 transition" title="View Details">
232
+ <ExternalLink size={16} className="inline-block" />
233
+ </button>
234
+ </td>
235
+ </tr>
236
+ ))
237
+ )}
238
+ </tbody>
239
+ </table>
240
+ </div>
241
+ </Card>
242
+ </div>
243
+ )
244
+ }