@theihtisham/ai-agent-starter-kit 1.0.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 (130) hide show
  1. package/.env.example +33 -0
  2. package/Dockerfile +35 -0
  3. package/LICENSE +21 -0
  4. package/README.md +73 -0
  5. package/docker-compose.yml +28 -0
  6. package/next-env.d.ts +5 -0
  7. package/next.config.mjs +17 -0
  8. package/package.json +85 -0
  9. package/postcss.config.js +6 -0
  10. package/prisma/schema.prisma +157 -0
  11. package/prisma/seed.ts +46 -0
  12. package/src/app/(auth)/forgot-password/page.tsx +56 -0
  13. package/src/app/(auth)/layout.tsx +7 -0
  14. package/src/app/(auth)/login/page.tsx +83 -0
  15. package/src/app/(auth)/signup/page.tsx +108 -0
  16. package/src/app/(dashboard)/agents/[id]/edit/page.tsx +68 -0
  17. package/src/app/(dashboard)/agents/[id]/page.tsx +114 -0
  18. package/src/app/(dashboard)/agents/new/page.tsx +43 -0
  19. package/src/app/(dashboard)/agents/page.tsx +63 -0
  20. package/src/app/(dashboard)/api-keys/page.tsx +139 -0
  21. package/src/app/(dashboard)/dashboard/page.tsx +79 -0
  22. package/src/app/(dashboard)/layout.tsx +16 -0
  23. package/src/app/(dashboard)/settings/billing/page.tsx +59 -0
  24. package/src/app/(dashboard)/settings/page.tsx +45 -0
  25. package/src/app/(dashboard)/usage/page.tsx +46 -0
  26. package/src/app/api/agents/[id]/chat/route.ts +100 -0
  27. package/src/app/api/agents/[id]/chats/route.ts +36 -0
  28. package/src/app/api/agents/[id]/route.ts +97 -0
  29. package/src/app/api/agents/route.ts +84 -0
  30. package/src/app/api/api-keys/[id]/route.ts +25 -0
  31. package/src/app/api/api-keys/route.ts +72 -0
  32. package/src/app/api/auth/[...nextauth]/route.ts +5 -0
  33. package/src/app/api/auth/register/route.ts +53 -0
  34. package/src/app/api/health/route.ts +26 -0
  35. package/src/app/api/stripe/checkout/route.ts +37 -0
  36. package/src/app/api/stripe/plans/route.ts +16 -0
  37. package/src/app/api/stripe/portal/route.ts +29 -0
  38. package/src/app/api/stripe/webhook/route.ts +45 -0
  39. package/src/app/api/usage/route.ts +43 -0
  40. package/src/app/globals.css +59 -0
  41. package/src/app/layout.tsx +22 -0
  42. package/src/app/page.tsx +32 -0
  43. package/src/app/pricing/page.tsx +25 -0
  44. package/src/components/agents/agent-form.tsx +137 -0
  45. package/src/components/agents/model-selector.tsx +35 -0
  46. package/src/components/agents/tool-selector.tsx +48 -0
  47. package/src/components/auth-provider.tsx +17 -0
  48. package/src/components/billing/plan-badge.tsx +23 -0
  49. package/src/components/billing/pricing-table.tsx +95 -0
  50. package/src/components/billing/usage-meter.tsx +39 -0
  51. package/src/components/chat/chat-input.tsx +68 -0
  52. package/src/components/chat/chat-interface.tsx +152 -0
  53. package/src/components/chat/chat-message.tsx +50 -0
  54. package/src/components/chat/chat-sidebar.tsx +49 -0
  55. package/src/components/chat/code-block.tsx +38 -0
  56. package/src/components/chat/markdown-renderer.tsx +56 -0
  57. package/src/components/chat/streaming-text.tsx +46 -0
  58. package/src/components/dashboard/agent-card.tsx +52 -0
  59. package/src/components/dashboard/header.tsx +75 -0
  60. package/src/components/dashboard/sidebar.tsx +52 -0
  61. package/src/components/dashboard/stat-card.tsx +42 -0
  62. package/src/components/dashboard/usage-chart.tsx +42 -0
  63. package/src/components/landing/cta.tsx +30 -0
  64. package/src/components/landing/features.tsx +75 -0
  65. package/src/components/landing/hero.tsx +42 -0
  66. package/src/components/landing/pricing.tsx +28 -0
  67. package/src/components/ui/avatar.tsx +24 -0
  68. package/src/components/ui/badge.tsx +24 -0
  69. package/src/components/ui/button.tsx +39 -0
  70. package/src/components/ui/card.tsx +50 -0
  71. package/src/components/ui/dialog.tsx +73 -0
  72. package/src/components/ui/dropdown.tsx +77 -0
  73. package/src/components/ui/input.tsx +23 -0
  74. package/src/components/ui/skeleton.tsx +7 -0
  75. package/src/components/ui/switch.tsx +31 -0
  76. package/src/components/ui/table.tsx +48 -0
  77. package/src/components/ui/tabs.tsx +66 -0
  78. package/src/components/ui/textarea.tsx +20 -0
  79. package/src/hooks/use-agent.ts +44 -0
  80. package/src/hooks/use-streaming.ts +82 -0
  81. package/src/hooks/use-subscription.ts +40 -0
  82. package/src/hooks/use-usage.ts +43 -0
  83. package/src/hooks/use-user.ts +13 -0
  84. package/src/lib/agents/index.ts +60 -0
  85. package/src/lib/agents/memory/long-term.ts +241 -0
  86. package/src/lib/agents/memory/manager.ts +154 -0
  87. package/src/lib/agents/memory/short-term.ts +155 -0
  88. package/src/lib/agents/memory/types.ts +68 -0
  89. package/src/lib/agents/orchestration/debate.ts +170 -0
  90. package/src/lib/agents/orchestration/index.ts +103 -0
  91. package/src/lib/agents/orchestration/parallel.ts +143 -0
  92. package/src/lib/agents/orchestration/router.ts +199 -0
  93. package/src/lib/agents/orchestration/sequential.ts +127 -0
  94. package/src/lib/agents/orchestration/types.ts +68 -0
  95. package/src/lib/agents/tools/calculator.ts +131 -0
  96. package/src/lib/agents/tools/code-executor.ts +191 -0
  97. package/src/lib/agents/tools/file-reader.ts +129 -0
  98. package/src/lib/agents/tools/index.ts +48 -0
  99. package/src/lib/agents/tools/registry.ts +182 -0
  100. package/src/lib/agents/tools/web-search.ts +83 -0
  101. package/src/lib/ai/agent.ts +275 -0
  102. package/src/lib/ai/context.ts +68 -0
  103. package/src/lib/ai/memory.ts +98 -0
  104. package/src/lib/ai/models.ts +80 -0
  105. package/src/lib/ai/streaming.ts +80 -0
  106. package/src/lib/ai/tools.ts +149 -0
  107. package/src/lib/auth/middleware.ts +41 -0
  108. package/src/lib/auth/nextauth.ts +69 -0
  109. package/src/lib/db/client.ts +15 -0
  110. package/src/lib/rate-limit/limiter.ts +93 -0
  111. package/src/lib/rate-limit/rules.ts +38 -0
  112. package/src/lib/stripe/client.ts +25 -0
  113. package/src/lib/stripe/plans.ts +75 -0
  114. package/src/lib/stripe/usage.ts +123 -0
  115. package/src/lib/stripe/webhooks.ts +96 -0
  116. package/src/lib/utils/api-response.ts +85 -0
  117. package/src/lib/utils/errors.ts +73 -0
  118. package/src/lib/utils/helpers.ts +50 -0
  119. package/src/lib/utils/id.ts +21 -0
  120. package/src/lib/utils/logger.ts +38 -0
  121. package/src/lib/utils/validation.ts +44 -0
  122. package/src/middleware.ts +13 -0
  123. package/src/types/agent.ts +31 -0
  124. package/src/types/api.ts +38 -0
  125. package/src/types/billing.ts +35 -0
  126. package/src/types/chat.ts +30 -0
  127. package/src/types/next-auth.d.ts +19 -0
  128. package/tailwind.config.ts +72 -0
  129. package/tsconfig.json +28 -0
  130. package/tsconfig.tsbuildinfo +1 -0
package/.env.example ADDED
@@ -0,0 +1,33 @@
1
+ # Database
2
+ DATABASE_URL="postgresql://postgres:postgres@localhost:5432/agentkit?schema=public"
3
+
4
+ # NextAuth
5
+ NEXTAUTH_URL="http://localhost:3000"
6
+ NEXTAUTH_SECRET="your-nextauth-secret-change-this-in-production"
7
+
8
+ # OAuth Providers (at least one required)
9
+ GOOGLE_CLIENT_ID=""
10
+ GOOGLE_CLIENT_SECRET=""
11
+ GITHUB_CLIENT_ID=""
12
+ GITHUB_CLIENT_SECRET=""
13
+
14
+ # Email Provider (Resend — for magic link auth)
15
+ RESEND_API_KEY=""
16
+ EMAIL_FROM="noreply@yourdomain.com"
17
+
18
+ # AI Providers (at least one required)
19
+ OPENAI_API_KEY=""
20
+ ANTHROPIC_API_KEY=""
21
+ GOOGLE_AI_API_KEY=""
22
+
23
+ # Stripe (for billing)
24
+ STRIPE_SECRET_KEY=""
25
+ STRIPE_WEBHOOK_SECRET=""
26
+ STRIPE_PRO_PRICE_ID=""
27
+ STRIPE_TEAM_PRICE_ID=""
28
+ NEXT_PUBLIC_STRIPE_PUBLISHABLE_KEY=""
29
+
30
+ # Optional
31
+ REDIS_URL="redis://localhost:6379"
32
+ NEXT_PUBLIC_APP_URL="http://localhost:3000"
33
+ NEXT_PUBLIC_APP_NAME="AI Agent Kit"
package/Dockerfile ADDED
@@ -0,0 +1,35 @@
1
+ FROM node:20-alpine AS base
2
+
3
+ # Install dependencies only when needed
4
+ FROM base AS deps
5
+ RUN apk add --no-cache libc6-compat
6
+ WORKDIR /app
7
+ COPY package.json package-lock.json* ./
8
+ RUN npm ci
9
+
10
+ # Build the application
11
+ FROM base AS builder
12
+ WORKDIR /app
13
+ COPY --from=deps /app/node_modules ./node_modules
14
+ COPY . .
15
+ RUN npx prisma generate
16
+ RUN npm run build
17
+
18
+ # Production image
19
+ FROM base AS runner
20
+ WORKDIR /app
21
+ ENV NODE_ENV=production
22
+
23
+ RUN addgroup --system --gid 1001 nodejs
24
+ RUN adduser --system --uid 1001 nextjs
25
+
26
+ COPY --from=builder /app/public ./public
27
+ COPY --from=builder --chown=nextjs:nodejs /app/.next/standalone ./
28
+ COPY --from=builder --chown=nextjs:nodejs /app/.next/static ./.next/static
29
+
30
+ USER nextjs
31
+ EXPOSE 3000
32
+ ENV PORT=3000
33
+ ENV HOSTNAME="0.0.0.0"
34
+
35
+ CMD ["node", "server.js"]
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md ADDED
@@ -0,0 +1,73 @@
1
+ # Ai Agent Starter Kit
2
+
3
+ Production-ready AI Agent framework with Next.js, Stripe billing, auth, and one-click deploy
4
+
5
+ ## Installation
6
+
7
+ ```bash
8
+ npm install @theihtisham/ai-agent-starter-kit
9
+ ```
10
+
11
+ ## Usage
12
+
13
+ ```typescript
14
+ import { } from '@theihtisham/ai-agent-starter-kit';
15
+ ```
16
+
17
+ ## Features
18
+
19
+ - Written in TypeScript with full type definitions
20
+ - Zero external dependencies (minimal footprint)
21
+ - Event-driven architecture
22
+ - Comprehensive test suite
23
+
24
+ ## API
25
+
26
+ ### Quick Start
27
+
28
+ ```typescript
29
+ import { } from '@theihtisham/ai-agent-starter-kit';
30
+
31
+ // Initialize and use the package
32
+ ```
33
+
34
+ ## Configuration
35
+
36
+ Configuration options and their defaults:
37
+
38
+ ```typescript
39
+ const config = {
40
+ // Add configuration options here
41
+ };
42
+ ```
43
+
44
+ ## Examples
45
+
46
+ See the `tests/` directory for usage examples.
47
+
48
+ ## Development
49
+
50
+ ```bash
51
+ # Install dependencies
52
+ npm install
53
+
54
+ # Build
55
+ npm run build
56
+
57
+ # Run tests
58
+ npm test
59
+
60
+ # Lint
61
+ npm run lint
62
+ ```
63
+
64
+ ## License
65
+
66
+ MIT License - see [LICENSE](LICENSE) for details.
67
+
68
+ ## Author
69
+
70
+ **ihtisham**
71
+
72
+ - GitHub: [https://github.com/ihtisham](https://github.com/ihtisham)
73
+ - npm: [@theihtisham](https://www.npmjs.com/~theihtisham)
@@ -0,0 +1,28 @@
1
+ version: '3.8'
2
+
3
+ services:
4
+ postgres:
5
+ image: postgres:16-alpine
6
+ container_name: agentkit-postgres
7
+ restart: unless-stopped
8
+ environment:
9
+ POSTGRES_USER: postgres
10
+ POSTGRES_PASSWORD: postgres
11
+ POSTGRES_DB: agentkit
12
+ ports:
13
+ - '5432:5432'
14
+ volumes:
15
+ - postgres_data:/var/lib/postgresql/data
16
+
17
+ redis:
18
+ image: redis:7-alpine
19
+ container_name: agentkit-redis
20
+ restart: unless-stopped
21
+ ports:
22
+ - '6379:6379'
23
+ volumes:
24
+ - redis_data:/data
25
+
26
+ volumes:
27
+ postgres_data:
28
+ redis_data:
package/next-env.d.ts ADDED
@@ -0,0 +1,5 @@
1
+ /// <reference types="next" />
2
+ /// <reference types="next/image-types/global" />
3
+
4
+ // NOTE: This file should not be edited
5
+ // see https://nextjs.org/docs/app/building-your-application/configuring/typescript for more information.
@@ -0,0 +1,17 @@
1
+ /** @type {import('next').NextConfig} */
2
+ const nextConfig = {
3
+ experimental: {
4
+ serverActions: {
5
+ bodySizeLimit: '2mb',
6
+ },
7
+ },
8
+ images: {
9
+ remotePatterns: [
10
+ { protocol: 'https', hostname: 'lh3.googleusercontent.com' },
11
+ { protocol: 'https', hostname: 'avatars.githubusercontent.com' },
12
+ { protocol: 'https', hostname: '**.stripe.com' },
13
+ ],
14
+ },
15
+ };
16
+
17
+ export default nextConfig;
package/package.json ADDED
@@ -0,0 +1,85 @@
1
+ {
2
+ "name": "@theihtisham/ai-agent-starter-kit",
3
+ "version": "1.0.0",
4
+ "description": "Production-ready AI Agent framework with Next.js, Stripe billing, auth, and one-click deploy",
5
+ "scripts": {
6
+ "dev": "next dev",
7
+ "build": "next build",
8
+ "start": "next start",
9
+ "lint": "next lint",
10
+ "db:generate": "prisma generate",
11
+ "db:push": "prisma db push",
12
+ "db:migrate": "prisma migrate dev",
13
+ "db:seed": "tsx prisma/seed.ts",
14
+ "db:studio": "prisma studio",
15
+ "postinstall": "prisma generate",
16
+ "type-check": "tsc --noEmit",
17
+ "test": "jest"
18
+ },
19
+ "dependencies": {
20
+ "@next-auth/prisma-adapter": "^1.0.7",
21
+ "@prisma/client": "^5.20.0",
22
+ "@stripe/stripe-js": "^4.5.0",
23
+ "bcryptjs": "^2.4.3",
24
+ "clsx": "^2.1.1",
25
+ "date-fns": "^4.1.0",
26
+ "lucide-react": "^0.451.0",
27
+ "nanoid": "^5.0.7",
28
+ "next": "^14.2.15",
29
+ "next-auth": "^4.24.8",
30
+ "next-themes": "^0.3.0",
31
+ "openai": "^4.67.0",
32
+ "react": "^18.3.1",
33
+ "react-dom": "^18.3.1",
34
+ "react-hot-toast": "^2.4.1",
35
+ "react-markdown": "^9.0.1",
36
+ "react-syntax-highlighter": "^15.5.0",
37
+ "recharts": "^3.8.1",
38
+ "redis": "^5.11.0",
39
+ "remark-gfm": "^4.0.0",
40
+ "resend": "^4.0.0",
41
+ "stripe": "^17.0.0",
42
+ "tailwind-merge": "^2.5.3",
43
+ "zod": "^3.23.8"
44
+ },
45
+ "devDependencies": {
46
+ "@types/bcryptjs": "^2.4.6",
47
+ "@types/node": "^22.7.9",
48
+ "@types/react": "^18.3.12",
49
+ "@types/react-dom": "^18.3.1",
50
+ "@types/react-syntax-highlighter": "^15.5.13",
51
+ "autoprefixer": "^10.4.20",
52
+ "eslint": "^8.57.1",
53
+ "eslint-config-next": "^14.2.15",
54
+ "postcss": "^8.4.47",
55
+ "prisma": "^5.20.0",
56
+ "tailwindcss": "^3.4.14",
57
+ "tsx": "^4.19.1",
58
+ "typescript": "^5.6.3",
59
+ "jest": "^29.7.0",
60
+ "ts-jest": "^29.1.0",
61
+ "@types/jest": "^29.5.0"
62
+ },
63
+ "license": "MIT",
64
+ "publishConfig": {
65
+ "access": "public"
66
+ },
67
+ "repository": {
68
+ "type": "git",
69
+ "url": "git+https://github.com/theihtisham/ai-agent-starter-kit.git"
70
+ },
71
+ "keywords": [
72
+ "ai",
73
+ "agent",
74
+ "nextjs",
75
+ "starter-kit",
76
+ "open-source",
77
+ "stripe",
78
+ "prisma"
79
+ ],
80
+ "author": "ihtisham",
81
+ "bugs": {
82
+ "url": "https://github.com/theihtisham/ai-agent-starter-kit/issues"
83
+ },
84
+ "homepage": "https://github.com/theihtisham/ai-agent-starter-kit#readme"
85
+ }
@@ -0,0 +1,6 @@
1
+ module.exports = {
2
+ plugins: {
3
+ tailwindcss: {},
4
+ autoprefixer: {},
5
+ },
6
+ };
@@ -0,0 +1,157 @@
1
+ // This is your Prisma schema file,
2
+ // learn more about it in the docs: https://pris.ly/d/prisma-schema
3
+
4
+ generator client {
5
+ provider = "prisma-client-js"
6
+ }
7
+
8
+ datasource db {
9
+ provider = "postgresql"
10
+ url = env("DATABASE_URL")
11
+ }
12
+
13
+ model User {
14
+ id String @id @default(cuid())
15
+ name String?
16
+ email String? @unique
17
+ emailVerified DateTime?
18
+ image String?
19
+ accounts Account[]
20
+ sessions Session[]
21
+ agents Agent[]
22
+ apiKeys ApiKey[]
23
+ subscription Subscription?
24
+ usage Usage[]
25
+ createdAt DateTime @default(now())
26
+ updatedAt DateTime @updatedAt
27
+ }
28
+
29
+ model Account {
30
+ id String @id @default(cuid())
31
+ userId String
32
+ type String
33
+ provider String
34
+ providerAccountId String
35
+ refresh_token String? @db.Text
36
+ access_token String? @db.Text
37
+ expires_at Int?
38
+ token_type String?
39
+ scope String?
40
+ id_token String? @db.Text
41
+ session_state String?
42
+ user User @relation(fields: [userId], references: [id], onDelete: Cascade)
43
+
44
+ @@unique([provider, providerAccountId])
45
+ @@index([userId])
46
+ }
47
+
48
+ model Session {
49
+ id String @id @default(cuid())
50
+ sessionToken String @unique
51
+ userId String
52
+ expires DateTime
53
+ user User @relation(fields: [userId], references: [id], onDelete: Cascade)
54
+
55
+ @@index([userId])
56
+ }
57
+
58
+ model VerificationToken {
59
+ identifier String
60
+ token String @unique
61
+ expires DateTime
62
+
63
+ @@unique([identifier, token])
64
+ }
65
+
66
+ model Agent {
67
+ id String @id @default(cuid())
68
+ userId String
69
+ name String
70
+ description String?
71
+ systemPrompt String @db.Text
72
+ model String @default("gpt-4o")
73
+ temperature Float @default(0.7)
74
+ maxTokens Int @default(4096)
75
+ tools Json @default("[]")
76
+ isPublic Boolean @default(false)
77
+ chats Chat[]
78
+ user User @relation(fields: [userId], references: [id], onDelete: Cascade)
79
+ createdAt DateTime @default(now())
80
+ updatedAt DateTime @updatedAt
81
+
82
+ @@index([userId])
83
+ @@index([isPublic])
84
+ }
85
+
86
+ model Chat {
87
+ id String @id @default(cuid())
88
+ agentId String
89
+ title String @default("New Chat")
90
+ messages Message[]
91
+ agent Agent @relation(fields: [agentId], references: [id], onDelete: Cascade)
92
+ createdAt DateTime @default(now())
93
+ updatedAt DateTime @updatedAt
94
+
95
+ @@index([agentId])
96
+ @@index([createdAt])
97
+ }
98
+
99
+ model Message {
100
+ id String @id @default(cuid())
101
+ chatId String
102
+ role String // "user" | "assistant" | "system" | "tool"
103
+ content String @db.Text
104
+ tokens Int?
105
+ metadata Json?
106
+ chat Chat @relation(fields: [chatId], references: [id], onDelete: Cascade)
107
+ createdAt DateTime @default(now())
108
+
109
+ @@index([chatId])
110
+ @@index([createdAt])
111
+ }
112
+
113
+ model ApiKey {
114
+ id String @id @default(cuid())
115
+ userId String
116
+ name String
117
+ key String @unique
118
+ prefix String // First 8 chars for display
119
+ lastUsed DateTime?
120
+ user User @relation(fields: [userId], references: [id], onDelete: Cascade)
121
+ createdAt DateTime @default(now())
122
+
123
+ @@index([userId])
124
+ @@index([key])
125
+ }
126
+
127
+ model Subscription {
128
+ id String @id @default(cuid())
129
+ userId String @unique
130
+ stripeCustomerId String @unique
131
+ stripePriceId String
132
+ stripeSubscriptionId String @unique
133
+ status String // active, past_due, canceled, trialing, incomplete
134
+ currentPeriodStart DateTime
135
+ currentPeriodEnd DateTime
136
+ cancelAtPeriodEnd Boolean @default(false)
137
+ user User @relation(fields: [userId], references: [id], onDelete: Cascade)
138
+ createdAt DateTime @default(now())
139
+ updatedAt DateTime @updatedAt
140
+
141
+ @@index([stripeCustomerId])
142
+ @@index([status])
143
+ }
144
+
145
+ model Usage {
146
+ id String @id @default(cuid())
147
+ userId String
148
+ agentId String?
149
+ type String // "message", "tool_call", "token_input", "token_output"
150
+ quantity Int
151
+ metadata Json?
152
+ user User @relation(fields: [userId], references: [id], onDelete: Cascade)
153
+ createdAt DateTime @default(now())
154
+
155
+ @@index([userId, createdAt])
156
+ @@index([userId, type, createdAt])
157
+ }
package/prisma/seed.ts ADDED
@@ -0,0 +1,46 @@
1
+ import { PrismaClient } from '@prisma/client';
2
+
3
+ const prisma = new PrismaClient();
4
+
5
+ async function main() {
6
+ console.log('Seeding database...');
7
+
8
+ // Create a demo user
9
+ const user = await prisma.user.upsert({
10
+ where: { email: 'demo@agentkit.dev' },
11
+ update: {},
12
+ create: {
13
+ email: 'demo@agentkit.dev',
14
+ name: 'Demo User',
15
+ },
16
+ });
17
+
18
+ // Create a demo agent
19
+ await prisma.agent.upsert({
20
+ where: { id: 'demo-agent' },
21
+ update: {},
22
+ create: {
23
+ id: 'demo-agent',
24
+ userId: user.id,
25
+ name: 'Demo Assistant',
26
+ description: 'A helpful AI assistant to get you started',
27
+ systemPrompt: 'You are a helpful AI assistant. Be concise, accurate, and friendly.',
28
+ model: 'gpt-4o-mini',
29
+ temperature: 0.7,
30
+ maxTokens: 4096,
31
+ tools: ['web_search', 'calculator', 'json_parser'],
32
+ isPublic: true,
33
+ },
34
+ });
35
+
36
+ console.log('Seed complete!');
37
+ }
38
+
39
+ main()
40
+ .catch((e) => {
41
+ console.error(e);
42
+ process.exit(1);
43
+ })
44
+ .finally(async () => {
45
+ await prisma.$disconnect();
46
+ });
@@ -0,0 +1,56 @@
1
+ 'use client';
2
+
3
+ import { useState } from 'react';
4
+ import Link from 'next/link';
5
+ import { Button } from '@/components/ui/button';
6
+ import { Input } from '@/components/ui/input';
7
+ import { Card, CardContent, CardHeader, CardTitle, CardDescription } from '@/components/ui/card';
8
+
9
+ export default function ForgotPasswordPage() {
10
+ const [email, setEmail] = useState('');
11
+ const [sent, setSent] = useState(false);
12
+ const [loading, setLoading] = useState(false);
13
+
14
+ const handleSubmit = async (e: React.FormEvent) => {
15
+ e.preventDefault();
16
+ setLoading(true);
17
+ // Email-based password reset via NextAuth email provider
18
+ // In production, call your API endpoint
19
+ setSent(true);
20
+ setLoading(false);
21
+ };
22
+
23
+ return (
24
+ <Card>
25
+ <CardHeader className="text-center">
26
+ <CardTitle className="text-2xl">Reset password</CardTitle>
27
+ <CardDescription>Enter your email to receive a reset link</CardDescription>
28
+ </CardHeader>
29
+ <CardContent>
30
+ {sent ? (
31
+ <div className="text-center space-y-4">
32
+ <p className="text-sm text-muted-foreground">
33
+ If an account exists with that email, you&apos;ll receive a reset link shortly.
34
+ </p>
35
+ <Link href="/login">
36
+ <Button variant="outline">Back to login</Button>
37
+ </Link>
38
+ </div>
39
+ ) : (
40
+ <form onSubmit={handleSubmit} className="space-y-4">
41
+ <div className="space-y-2">
42
+ <label className="text-sm font-medium">Email</label>
43
+ <Input type="email" value={email} onChange={(e) => setEmail(e.target.value)} required />
44
+ </div>
45
+ <Button type="submit" className="w-full" disabled={loading}>
46
+ {loading ? 'Sending...' : 'Send reset link'}
47
+ </Button>
48
+ <div className="text-center">
49
+ <Link href="/login" className="text-sm text-primary hover:underline">Back to login</Link>
50
+ </div>
51
+ </form>
52
+ )}
53
+ </CardContent>
54
+ </Card>
55
+ );
56
+ }
@@ -0,0 +1,7 @@
1
+ export default function AuthLayout({ children }: { children: React.ReactNode }) {
2
+ return (
3
+ <div className="min-h-screen flex items-center justify-center bg-muted/50">
4
+ <div className="w-full max-w-md">{children}</div>
5
+ </div>
6
+ );
7
+ }
@@ -0,0 +1,83 @@
1
+ 'use client';
2
+
3
+ import { useState } from 'react';
4
+ import { signIn } from 'next-auth/react';
5
+ import { useRouter } from 'next/navigation';
6
+ import Link from 'next/link';
7
+ import { Button } from '@/components/ui/button';
8
+ import { Input } from '@/components/ui/input';
9
+ import { Card, CardContent, CardHeader, CardTitle, CardDescription, CardFooter } from '@/components/ui/card';
10
+
11
+ export default function LoginPage() {
12
+ const router = useRouter();
13
+ const [email, setEmail] = useState('');
14
+ const [password, setPassword] = useState('');
15
+ const [error, setError] = useState('');
16
+ const [loading, setLoading] = useState(false);
17
+
18
+ const handleSubmit = async (e: React.FormEvent) => {
19
+ e.preventDefault();
20
+ setLoading(true);
21
+ setError('');
22
+
23
+ const result = await signIn('credentials', {
24
+ email,
25
+ password,
26
+ redirect: false,
27
+ });
28
+
29
+ if (result?.error) {
30
+ setError('Invalid credentials');
31
+ setLoading(false);
32
+ } else {
33
+ router.push('/dashboard');
34
+ }
35
+ };
36
+
37
+ return (
38
+ <Card>
39
+ <CardHeader className="text-center">
40
+ <CardTitle className="text-2xl">Welcome back</CardTitle>
41
+ <CardDescription>Sign in to your AgentKit account</CardDescription>
42
+ </CardHeader>
43
+ <CardContent>
44
+ <div className="grid gap-4">
45
+ <div className="grid grid-cols-2 gap-3">
46
+ <Button variant="outline" onClick={() => signIn('google', { callbackUrl: '/dashboard' })}>
47
+ Google
48
+ </Button>
49
+ <Button variant="outline" onClick={() => signIn('github', { callbackUrl: '/dashboard' })}>
50
+ GitHub
51
+ </Button>
52
+ </div>
53
+ <div className="relative">
54
+ <div className="absolute inset-0 flex items-center"><span className="w-full border-t" /></div>
55
+ <div className="relative flex justify-center text-xs uppercase">
56
+ <span className="bg-card px-2 text-muted-foreground">or continue with email</span>
57
+ </div>
58
+ </div>
59
+ <form onSubmit={handleSubmit} className="space-y-4">
60
+ <div className="space-y-2">
61
+ <label className="text-sm font-medium">Email</label>
62
+ <Input type="email" value={email} onChange={(e) => setEmail(e.target.value)} required />
63
+ </div>
64
+ <div className="space-y-2">
65
+ <label className="text-sm font-medium">Password</label>
66
+ <Input type="password" value={password} onChange={(e) => setPassword(e.target.value)} required />
67
+ </div>
68
+ {error && <p className="text-sm text-destructive">{error}</p>}
69
+ <Button type="submit" className="w-full" disabled={loading}>
70
+ {loading ? 'Signing in...' : 'Sign in'}
71
+ </Button>
72
+ </form>
73
+ </div>
74
+ </CardContent>
75
+ <CardFooter className="justify-center">
76
+ <p className="text-sm text-muted-foreground">
77
+ Don&apos;t have an account?{' '}
78
+ <Link href="/signup" className="text-primary hover:underline">Sign up</Link>
79
+ </p>
80
+ </CardFooter>
81
+ </Card>
82
+ );
83
+ }