@digilogiclabs/create-saas-app 2.8.0 → 2.9.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 (94) hide show
  1. package/dist/.tsbuildinfo +1 -1
  2. package/dist/generators/template-generator.js +8 -8
  3. package/dist/generators/template-generator.js.map +1 -1
  4. package/dist/templates/shared/quality/web/src/__tests__/accessibility.test.tsx +3 -3
  5. package/dist/templates/web/ai-platform/template/src/app/page.tsx +207 -207
  6. package/dist/templates/web/base/template/package.json +1 -3
  7. package/dist/templates/web/base/template/src/app/auth/callback/route.ts +32 -18
  8. package/dist/templates/web/base/template/src/app/dashboard/page.tsx +6 -43
  9. package/dist/templates/web/base/template/src/app/globals.css +158 -157
  10. package/dist/templates/web/base/template/src/app/page.tsx +2 -2
  11. package/dist/templates/web/ui-auth/template/src/app/dev-setup/page.tsx +800 -800
  12. package/dist/templates/web/ui-auth/template/src/app/globals.css +96 -95
  13. package/dist/templates/web/ui-auth/template/src/app/login/page.tsx +109 -109
  14. package/dist/templates/web/ui-auth/template/src/app/page.tsx +4 -3
  15. package/dist/templates/web/ui-auth/template/src/app/signup/page.tsx +128 -128
  16. package/dist/templates/web/ui-auth-ai/template/src/app/globals.css +35 -40
  17. package/dist/templates/web/ui-auth-ai/template/src/app/layout.tsx +1 -0
  18. package/dist/templates/web/ui-auth-payments/template/src/app/checkout/page.tsx +3 -3
  19. package/dist/templates/web/ui-auth-payments/template/src/app/dashboard/page.tsx +10 -49
  20. package/dist/templates/web/ui-auth-payments/template/src/app/dev-setup/page.tsx +800 -800
  21. package/dist/templates/web/ui-auth-payments/template/src/app/globals.css +212 -211
  22. package/dist/templates/web/ui-auth-payments/template/src/app/login/page.tsx +109 -109
  23. package/dist/templates/web/ui-auth-payments/template/src/app/page.tsx +350 -350
  24. package/dist/templates/web/ui-auth-payments/template/src/app/setup/page.tsx +506 -506
  25. package/dist/templates/web/ui-auth-payments/template/src/app/signup/page.tsx +128 -128
  26. package/dist/templates/web/ui-auth-payments/template/src/components/client/login-form.tsx +143 -143
  27. package/dist/templates/web/ui-auth-payments/template/src/components/client/signup-form.tsx +184 -184
  28. package/dist/templates/web/ui-auth-payments-ai/template/src/app/billing/page.tsx +143 -233
  29. package/dist/templates/web/ui-auth-payments-ai/template/src/app/dashboard/page.tsx +10 -50
  30. package/dist/templates/web/ui-auth-payments-ai/template/src/app/dev-setup/page.tsx +800 -800
  31. package/dist/templates/web/ui-auth-payments-ai/template/src/app/globals.css +97 -96
  32. package/dist/templates/web/ui-auth-payments-ai/template/src/app/onboarding/page.tsx +325 -364
  33. package/dist/templates/web/ui-auth-payments-ai/template/src/app/page.tsx +1 -1
  34. package/dist/templates/web/ui-auth-payments-ai/template/src/app/settings/page.tsx +389 -532
  35. package/dist/templates/web/ui-auth-payments-ai/template/src/app/setup/page.tsx +644 -644
  36. package/dist/templates/web/ui-auth-payments-ai/template/src/components/client/login-form.tsx +119 -163
  37. package/dist/templates/web/ui-auth-payments-ai/template/src/components/client/signup-form.tsx +158 -201
  38. package/dist/templates/web/ui-auth-payments-ai-rag/template/package.json +1 -2
  39. package/dist/templates/web/ui-auth-payments-audio/template/src/app/dashboard/page.tsx +10 -51
  40. package/dist/templates/web/ui-auth-payments-audio/template/src/app/globals.css +97 -96
  41. package/dist/templates/web/ui-auth-payments-audio/template/src/app/page.tsx +402 -403
  42. package/dist/templates/web/ui-auth-payments-audio/template/src/components/client/login-form.tsx +143 -143
  43. package/dist/templates/web/ui-auth-payments-audio/template/src/components/client/signup-form.tsx +184 -184
  44. package/dist/templates/web/ui-auth-payments-video/template/src/app/globals.css +229 -228
  45. package/dist/templates/web/ui-auth-payments-video/template/src/app/login/page.tsx +1 -1
  46. package/dist/templates/web/ui-auth-payments-video/template/src/app/page.tsx +4 -7
  47. package/dist/templates/web/ui-auth-payments-video/template/src/app/signup/page.tsx +1 -1
  48. package/dist/templates/web/ui-only/template/src/app/globals.css +43 -42
  49. package/package.json +1 -1
  50. package/src/templates/shared/quality/web/src/__tests__/accessibility.test.tsx +3 -3
  51. package/src/templates/web/ai-platform/template/src/app/page.tsx +207 -207
  52. package/src/templates/web/base/template/package.json +1 -3
  53. package/src/templates/web/base/template/src/app/auth/callback/route.ts +32 -18
  54. package/src/templates/web/base/template/src/app/dashboard/page.tsx +6 -43
  55. package/src/templates/web/base/template/src/app/globals.css +158 -157
  56. package/src/templates/web/base/template/src/app/page.tsx +2 -2
  57. package/src/templates/web/ui-auth/template/src/app/dev-setup/page.tsx +800 -800
  58. package/src/templates/web/ui-auth/template/src/app/globals.css +96 -95
  59. package/src/templates/web/ui-auth/template/src/app/login/page.tsx +109 -109
  60. package/src/templates/web/ui-auth/template/src/app/page.tsx +4 -3
  61. package/src/templates/web/ui-auth/template/src/app/signup/page.tsx +128 -128
  62. package/src/templates/web/ui-auth-ai/template/src/app/globals.css +35 -40
  63. package/src/templates/web/ui-auth-ai/template/src/app/layout.tsx +1 -0
  64. package/src/templates/web/ui-auth-payments/template/src/app/checkout/page.tsx +3 -3
  65. package/src/templates/web/ui-auth-payments/template/src/app/dashboard/page.tsx +10 -49
  66. package/src/templates/web/ui-auth-payments/template/src/app/dev-setup/page.tsx +800 -800
  67. package/src/templates/web/ui-auth-payments/template/src/app/globals.css +212 -211
  68. package/src/templates/web/ui-auth-payments/template/src/app/login/page.tsx +109 -109
  69. package/src/templates/web/ui-auth-payments/template/src/app/page.tsx +350 -350
  70. package/src/templates/web/ui-auth-payments/template/src/app/setup/page.tsx +506 -506
  71. package/src/templates/web/ui-auth-payments/template/src/app/signup/page.tsx +128 -128
  72. package/src/templates/web/ui-auth-payments/template/src/components/client/login-form.tsx +143 -143
  73. package/src/templates/web/ui-auth-payments/template/src/components/client/signup-form.tsx +184 -184
  74. package/src/templates/web/ui-auth-payments-ai/template/src/app/billing/page.tsx +143 -233
  75. package/src/templates/web/ui-auth-payments-ai/template/src/app/dashboard/page.tsx +10 -50
  76. package/src/templates/web/ui-auth-payments-ai/template/src/app/dev-setup/page.tsx +800 -800
  77. package/src/templates/web/ui-auth-payments-ai/template/src/app/globals.css +97 -96
  78. package/src/templates/web/ui-auth-payments-ai/template/src/app/onboarding/page.tsx +325 -364
  79. package/src/templates/web/ui-auth-payments-ai/template/src/app/page.tsx +1 -1
  80. package/src/templates/web/ui-auth-payments-ai/template/src/app/settings/page.tsx +389 -532
  81. package/src/templates/web/ui-auth-payments-ai/template/src/app/setup/page.tsx +644 -644
  82. package/src/templates/web/ui-auth-payments-ai/template/src/components/client/login-form.tsx +119 -163
  83. package/src/templates/web/ui-auth-payments-ai/template/src/components/client/signup-form.tsx +158 -201
  84. package/src/templates/web/ui-auth-payments-ai-rag/template/package.json +1 -2
  85. package/src/templates/web/ui-auth-payments-audio/template/src/app/dashboard/page.tsx +10 -51
  86. package/src/templates/web/ui-auth-payments-audio/template/src/app/globals.css +97 -96
  87. package/src/templates/web/ui-auth-payments-audio/template/src/app/page.tsx +402 -403
  88. package/src/templates/web/ui-auth-payments-audio/template/src/components/client/login-form.tsx +143 -143
  89. package/src/templates/web/ui-auth-payments-audio/template/src/components/client/signup-form.tsx +184 -184
  90. package/src/templates/web/ui-auth-payments-video/template/src/app/globals.css +229 -228
  91. package/src/templates/web/ui-auth-payments-video/template/src/app/login/page.tsx +1 -1
  92. package/src/templates/web/ui-auth-payments-video/template/src/app/page.tsx +4 -7
  93. package/src/templates/web/ui-auth-payments-video/template/src/app/signup/page.tsx +1 -1
  94. package/src/templates/web/ui-only/template/src/app/globals.css +43 -42
@@ -1,211 +1,212 @@
1
- @tailwind base;
2
- @tailwind components;
3
- @tailwind utilities;
4
-
5
- /* Import SaaS Factory UI styles */
6
- @import '@digilogiclabs/saas-factory-ui/dist/index.css';
7
-
8
- @layer base {
9
- :root {
10
- --background: 0 0% 100%;
11
- --foreground: 222.2 84% 4.9%;
12
- --card: 0 0% 100%;
13
- --card-foreground: 222.2 84% 4.9%;
14
- --primary: 221.2 83.2% 53.3%;
15
- --primary-foreground: 210 40% 98%;
16
- --secondary: 210 40% 96%;
17
- --secondary-foreground: 222.2 84% 4.9%;
18
- --border: 214.3 31.8% 91.4%;
19
- --radius: 0.5rem;
20
- }
21
-
22
- .dark {
23
- --background: 222.2 84% 4.9%;
24
- --foreground: 210 40% 98%;
25
- --card: 222.2 84% 4.9%;
26
- --card-foreground: 210 40% 98%;
27
- --primary: 217.2 91.2% 59.8%;
28
- --primary-foreground: 222.2 84% 4.9%;
29
- --secondary: 217.2 32.6% 17.5%;
30
- --secondary-foreground: 210 40% 98%;
31
- --border: 217.2 32.6% 17.5%;
32
- }
33
- }
34
-
35
- @layer base {
36
- * {
37
- @apply border-border;
38
- }
39
- body {
40
- @apply bg-background text-foreground;
41
- }
42
- }
43
-
44
- /* Mobile-first optimizations */
45
- @media (max-width: 768px) {
46
- .mobile-optimized {
47
- touch-action: manipulation;
48
- -webkit-tap-highlight-color: transparent;
49
- }
50
-
51
- /* Better touch targets */
52
- button,
53
- a,
54
- input,
55
- select,
56
- textarea {
57
- min-height: 44px;
58
- min-width: 44px;
59
- }
60
-
61
- /* Smooth scrolling for mobile */
62
- html {
63
- scroll-behavior: smooth;
64
- -webkit-overflow-scrolling: touch;
65
- }
66
- }
67
-
68
- /* Animated moving banner */
69
- @keyframes marquee {
70
- 0% {
71
- transform: translate3d(100%, 0, 0);
72
- }
73
- 100% {
74
- transform: translate3d(-100%, 0, 0);
75
- }
76
- }
77
-
78
- .animate-marquee {
79
- animation: marquee 15s linear infinite;
80
- }
81
-
82
- /* Network-aware styles */
83
- @media (prefers-reduced-data: reduce) {
84
- .high-bandwidth-content {
85
- display: none;
86
- }
87
- }
88
-
89
- /* Reduced motion preferences */
90
- @media (prefers-reduced-motion: reduce) {
91
- *,
92
- *::before,
93
- *::after {
94
- animation-duration: 0.01ms !important;
95
- animation-iteration-count: 1 !important;
96
- transition-duration: 0.01ms !important;
97
- }
98
-
99
- .animate-marquee {
100
- animation: none;
101
- }
102
- }
103
-
104
- /* Hamburger menu animations */
105
- .hamburger-line {
106
- transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
107
- transform-origin: center;
108
- }
109
-
110
- .hamburger-open .hamburger-line:nth-child(1) {
111
- transform: rotate(45deg) translate(6px, 6px);
112
- }
113
-
114
- .hamburger-open .hamburger-line:nth-child(2) {
115
- opacity: 0;
116
- }
117
-
118
- .hamburger-open .hamburger-line:nth-child(3) {
119
- transform: rotate(-45deg) translate(6px, -6px);
120
- }
121
-
122
- /* Custom animations for mobile interactions */
123
- @keyframes haptic-feedback {
124
- 0% { transform: scale(1); }
125
- 50% { transform: scale(0.95); }
126
- 100% { transform: scale(1); }
127
- }
128
-
129
- .haptic-feedback {
130
- animation: haptic-feedback 0.1s ease-in-out;
131
- }
132
-
133
- /* Offline indicator styles */
134
- .offline-indicator {
135
- position: fixed;
136
- top: 0;
137
- left: 0;
138
- right: 0;
139
- background: #f59e0b;
140
- color: white;
141
- text-align: center;
142
- padding: 8px;
143
- font-size: 14px;
144
- z-index: 9999;
145
- }
146
-
147
- /* Loading states */
148
- .loading-skeleton {
149
- background: linear-gradient(90deg, #f0f0f0 25%, #e0e0e0 50%, #f0f0f0 75%);
150
- background-size: 200% 100%;
151
- animation: loading 1.5s infinite;
152
- }
153
-
154
- @keyframes loading {
155
- 0% {
156
- background-position: 200% 0;
157
- }
158
- 100% {
159
- background-position: -200% 0;
160
- }
161
- }
162
-
163
- /* Progressive image loading */
164
- .progressive-image {
165
- filter: blur(5px);
166
- transition: filter 0.3s;
167
- }
168
-
169
- .progressive-image.loaded {
170
- filter: blur(0);
171
- }
172
-
173
- /* Additional custom animations for enhanced visual effects */
174
- @keyframes slide-down {
175
- from {
176
- opacity: 0;
177
- transform: translateY(-10px);
178
- }
179
- to {
180
- opacity: 1;
181
- transform: translateY(0);
182
- }
183
- }
184
-
185
- @keyframes fade-in-up {
186
- from {
187
- opacity: 0;
188
- transform: translateY(10px);
189
- }
190
- to {
191
- opacity: 1;
192
- transform: translateY(0);
193
- }
194
- }
195
-
196
- .animate-slide-down {
197
- animation: slide-down 0.6s ease-out;
198
- }
199
-
200
- .animate-fade-in-up {
201
- animation: fade-in-up 0.6s ease-out;
202
- animation-fill-mode: both;
203
- }
204
-
205
- .animation-delay-2000 {
206
- animation-delay: 2s;
207
- }
208
-
209
- .animation-delay-4000 {
210
- animation-delay: 4s;
211
- }
1
+ /* Import SaaS Factory UI styles */
2
+ @import '@digilogiclabs/saas-factory-ui/dist/index.css';
3
+
4
+ @tailwind base;
5
+ @tailwind components;
6
+ @tailwind utilities;
7
+
8
+
9
+ @layer base {
10
+ :root {
11
+ --background: 0 0% 100%;
12
+ --foreground: 222.2 84% 4.9%;
13
+ --card: 0 0% 100%;
14
+ --card-foreground: 222.2 84% 4.9%;
15
+ --primary: 221.2 83.2% 53.3%;
16
+ --primary-foreground: 210 40% 98%;
17
+ --secondary: 210 40% 96%;
18
+ --secondary-foreground: 222.2 84% 4.9%;
19
+ --border: 214.3 31.8% 91.4%;
20
+ --radius: 0.5rem;
21
+ }
22
+
23
+ .dark {
24
+ --background: 222.2 84% 4.9%;
25
+ --foreground: 210 40% 98%;
26
+ --card: 222.2 84% 4.9%;
27
+ --card-foreground: 210 40% 98%;
28
+ --primary: 217.2 91.2% 59.8%;
29
+ --primary-foreground: 222.2 84% 4.9%;
30
+ --secondary: 217.2 32.6% 17.5%;
31
+ --secondary-foreground: 210 40% 98%;
32
+ --border: 217.2 32.6% 17.5%;
33
+ }
34
+ }
35
+
36
+ @layer base {
37
+ * {
38
+ @apply border-border;
39
+ }
40
+ body {
41
+ @apply bg-background text-foreground;
42
+ }
43
+ }
44
+
45
+ /* Mobile-first optimizations */
46
+ @media (max-width: 768px) {
47
+ .mobile-optimized {
48
+ touch-action: manipulation;
49
+ -webkit-tap-highlight-color: transparent;
50
+ }
51
+
52
+ /* Better touch targets */
53
+ button,
54
+ a,
55
+ input,
56
+ select,
57
+ textarea {
58
+ min-height: 44px;
59
+ min-width: 44px;
60
+ }
61
+
62
+ /* Smooth scrolling for mobile */
63
+ html {
64
+ scroll-behavior: smooth;
65
+ -webkit-overflow-scrolling: touch;
66
+ }
67
+ }
68
+
69
+ /* Animated moving banner */
70
+ @keyframes marquee {
71
+ 0% {
72
+ transform: translate3d(100%, 0, 0);
73
+ }
74
+ 100% {
75
+ transform: translate3d(-100%, 0, 0);
76
+ }
77
+ }
78
+
79
+ .animate-marquee {
80
+ animation: marquee 15s linear infinite;
81
+ }
82
+
83
+ /* Network-aware styles */
84
+ @media (prefers-reduced-data: reduce) {
85
+ .high-bandwidth-content {
86
+ display: none;
87
+ }
88
+ }
89
+
90
+ /* Reduced motion preferences */
91
+ @media (prefers-reduced-motion: reduce) {
92
+ *,
93
+ *::before,
94
+ *::after {
95
+ animation-duration: 0.01ms !important;
96
+ animation-iteration-count: 1 !important;
97
+ transition-duration: 0.01ms !important;
98
+ }
99
+
100
+ .animate-marquee {
101
+ animation: none;
102
+ }
103
+ }
104
+
105
+ /* Hamburger menu animations */
106
+ .hamburger-line {
107
+ transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
108
+ transform-origin: center;
109
+ }
110
+
111
+ .hamburger-open .hamburger-line:nth-child(1) {
112
+ transform: rotate(45deg) translate(6px, 6px);
113
+ }
114
+
115
+ .hamburger-open .hamburger-line:nth-child(2) {
116
+ opacity: 0;
117
+ }
118
+
119
+ .hamburger-open .hamburger-line:nth-child(3) {
120
+ transform: rotate(-45deg) translate(6px, -6px);
121
+ }
122
+
123
+ /* Custom animations for mobile interactions */
124
+ @keyframes haptic-feedback {
125
+ 0% { transform: scale(1); }
126
+ 50% { transform: scale(0.95); }
127
+ 100% { transform: scale(1); }
128
+ }
129
+
130
+ .haptic-feedback {
131
+ animation: haptic-feedback 0.1s ease-in-out;
132
+ }
133
+
134
+ /* Offline indicator styles */
135
+ .offline-indicator {
136
+ position: fixed;
137
+ top: 0;
138
+ left: 0;
139
+ right: 0;
140
+ background: #f59e0b;
141
+ color: white;
142
+ text-align: center;
143
+ padding: 8px;
144
+ font-size: 14px;
145
+ z-index: 9999;
146
+ }
147
+
148
+ /* Loading states */
149
+ .loading-skeleton {
150
+ background: linear-gradient(90deg, #f0f0f0 25%, #e0e0e0 50%, #f0f0f0 75%);
151
+ background-size: 200% 100%;
152
+ animation: loading 1.5s infinite;
153
+ }
154
+
155
+ @keyframes loading {
156
+ 0% {
157
+ background-position: 200% 0;
158
+ }
159
+ 100% {
160
+ background-position: -200% 0;
161
+ }
162
+ }
163
+
164
+ /* Progressive image loading */
165
+ .progressive-image {
166
+ filter: blur(5px);
167
+ transition: filter 0.3s;
168
+ }
169
+
170
+ .progressive-image.loaded {
171
+ filter: blur(0);
172
+ }
173
+
174
+ /* Additional custom animations for enhanced visual effects */
175
+ @keyframes slide-down {
176
+ from {
177
+ opacity: 0;
178
+ transform: translateY(-10px);
179
+ }
180
+ to {
181
+ opacity: 1;
182
+ transform: translateY(0);
183
+ }
184
+ }
185
+
186
+ @keyframes fade-in-up {
187
+ from {
188
+ opacity: 0;
189
+ transform: translateY(10px);
190
+ }
191
+ to {
192
+ opacity: 1;
193
+ transform: translateY(0);
194
+ }
195
+ }
196
+
197
+ .animate-slide-down {
198
+ animation: slide-down 0.6s ease-out;
199
+ }
200
+
201
+ .animate-fade-in-up {
202
+ animation: fade-in-up 0.6s ease-out;
203
+ animation-fill-mode: both;
204
+ }
205
+
206
+ .animation-delay-2000 {
207
+ animation-delay: 2s;
208
+ }
209
+
210
+ .animation-delay-4000 {
211
+ animation-delay: 4s;
212
+ }
@@ -1,109 +1,109 @@
1
- 'use client';
2
-
3
- import React, { useState } from 'react';
4
- import { Button, Card, Input, Label } from '@digilogiclabs/saas-factory-ui';
5
- import { useAuth } from '@digilogiclabs/app-sdk';
6
- import { useRouter } from 'next/navigation';
7
-
8
- export default function LoginPage() {
9
- const [email, setEmail] = useState('');
10
- const [password, setPassword] = useState('');
11
- const { signIn, signInWithOAuth, loading, error, user } = useAuth();
12
- const router = useRouter();
13
-
14
- // Redirect if already logged in
15
- React.useEffect(() => {
16
- if (user) {
17
- router.push('/');
18
- }
19
- }, [user, router]);
20
-
21
- const handleLogin = async (e: React.FormEvent) => {
22
- e.preventDefault();
23
- try {
24
- await signIn(email, password);
25
- router.push('/');
26
- } catch (err) {
27
- console.error('Login error:', err);
28
- }
29
- };
30
-
31
- const handleGoogleLogin = async () => {
32
- try {
33
- await signInWithOAuth('google', window.location.origin);
34
- } catch (err) {
35
- console.error('Google login error:', err);
36
- }
37
- };
38
-
39
- if (loading) {
40
- return (
41
- <div className="flex items-center justify-center min-h-screen bg-gray-100">
42
- <div>Loading...</div>
43
- </div>
44
- );
45
- }
46
-
47
- return (
48
- <div className="flex items-center justify-center min-h-screen bg-gray-100">
49
- <Card className="w-full max-w-md p-8">
50
- <h1 className="text-2xl font-bold text-center mb-6">Sign In</h1>
51
-
52
- {error && (
53
- <div className="mb-4 p-3 bg-red-100 border border-red-400 text-red-700 rounded">
54
- {error.message}
55
- </div>
56
- )}
57
-
58
- <form onSubmit={handleLogin} className="space-y-4">
59
- <div>
60
- <Label htmlFor="email">Email</Label>
61
- <Input
62
- id="email"
63
- type="email"
64
- value={email}
65
- onChange={(e) => setEmail(e.target.value)}
66
- placeholder="Enter your email"
67
- required
68
- disabled={loading}
69
- />
70
- </div>
71
- <div>
72
- <Label htmlFor="password">Password</Label>
73
- <Input
74
- id="password"
75
- type="password"
76
- value={password}
77
- onChange={(e) => setPassword(e.target.value)}
78
- placeholder="Enter your password"
79
- required
80
- disabled={loading}
81
- />
82
- </div>
83
- <Button type="submit" className="w-full" disabled={loading}>
84
- {loading ? 'Signing In...' : 'Sign In'}
85
- </Button>
86
- <Button
87
- type="button"
88
- variant="outline"
89
- className="w-full"
90
- onClick={handleGoogleLogin}
91
- disabled={loading}
92
- >
93
- Sign in with Google
94
- </Button>
95
- </form>
96
-
97
- <div className="mt-4 text-center">
98
- <p className="text-sm text-gray-600">
99
- Don&apos;t have an account?{' '}
100
- <a href="/signup" className="text-blue-600 hover:underline">
101
- Sign up
102
- </a>
103
- </p>
104
- </div>
105
- </Card>
106
- </div>
107
- );
108
- }
109
-
1
+ 'use client';
2
+
3
+ import React, { useState } from 'react';
4
+ import { Button, Card, Input, Label } from '@digilogiclabs/saas-factory-ui';
5
+ import { useAuth } from '@digilogiclabs/app-sdk';
6
+ import { useRouter } from 'next/navigation';
7
+
8
+ export default function LoginPage() {
9
+ const [email, setEmail] = useState('');
10
+ const [password, setPassword] = useState('');
11
+ const { signIn, signInWithOAuth, loading, error, user } = useAuth();
12
+ const router = useRouter();
13
+
14
+ // Redirect if already logged in
15
+ React.useEffect(() => {
16
+ if (user) {
17
+ router.push('/');
18
+ }
19
+ }, [user, router]);
20
+
21
+ const handleLogin = async (e: React.FormEvent) => {
22
+ e.preventDefault();
23
+ try {
24
+ await signIn(email, password);
25
+ router.push('/');
26
+ } catch (err) {
27
+ console.error('Login error:', err);
28
+ }
29
+ };
30
+
31
+ const handleGoogleLogin = async () => {
32
+ try {
33
+ await signInWithOAuth('google');
34
+ } catch (err) {
35
+ console.error('Google login error:', err);
36
+ }
37
+ };
38
+
39
+ if (loading) {
40
+ return (
41
+ <div className="flex items-center justify-center min-h-screen bg-gray-100">
42
+ <div>Loading...</div>
43
+ </div>
44
+ );
45
+ }
46
+
47
+ return (
48
+ <div className="flex items-center justify-center min-h-screen bg-gray-100">
49
+ <Card className="w-full max-w-md p-8">
50
+ <h1 className="text-2xl font-bold text-center mb-6">Sign In</h1>
51
+
52
+ {error && (
53
+ <div className="mb-4 p-3 bg-red-100 border border-red-400 text-red-700 rounded">
54
+ {error.message}
55
+ </div>
56
+ )}
57
+
58
+ <form onSubmit={handleLogin} className="space-y-4">
59
+ <div>
60
+ <Label htmlFor="email">Email</Label>
61
+ <Input
62
+ id="email"
63
+ type="email"
64
+ value={email}
65
+ onChange={(e) => setEmail(e.target.value)}
66
+ placeholder="Enter your email"
67
+ required
68
+ disabled={loading}
69
+ />
70
+ </div>
71
+ <div>
72
+ <Label htmlFor="password">Password</Label>
73
+ <Input
74
+ id="password"
75
+ type="password"
76
+ value={password}
77
+ onChange={(e) => setPassword(e.target.value)}
78
+ placeholder="Enter your password"
79
+ required
80
+ disabled={loading}
81
+ />
82
+ </div>
83
+ <Button type="submit" className="w-full" disabled={loading}>
84
+ {loading ? 'Signing In...' : 'Sign In'}
85
+ </Button>
86
+ <Button
87
+ type="button"
88
+ variant="outline"
89
+ className="w-full"
90
+ onClick={handleGoogleLogin}
91
+ disabled={loading}
92
+ >
93
+ Sign in with Google
94
+ </Button>
95
+ </form>
96
+
97
+ <div className="mt-4 text-center">
98
+ <p className="text-sm text-gray-600">
99
+ Don&apos;t have an account?{' '}
100
+ <a href="/signup" className="text-blue-600 hover:underline">
101
+ Sign up
102
+ </a>
103
+ </p>
104
+ </div>
105
+ </Card>
106
+ </div>
107
+ );
108
+ }
109
+