@ezcoder.dev/sdk 1.0.0 → 1.2.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 (53) hide show
  1. package/dist/DatabaseProvider-DalP-KHC.d.ts +167 -0
  2. package/dist/analytics/index.d.ts +22 -1
  3. package/dist/analytics/index.js +79 -4
  4. package/dist/analytics/index.js.map +1 -1
  5. package/dist/animation/index.js.map +1 -1
  6. package/dist/auth/index.d.ts +2 -1
  7. package/dist/auth/index.js +25 -6
  8. package/dist/auth/index.js.map +1 -1
  9. package/dist/chunk-CQKYANAW.js +44 -0
  10. package/dist/chunk-CQKYANAW.js.map +1 -0
  11. package/dist/{chunk-5XIZHBKE.js → chunk-HJ2EIZ4S.js} +23 -6
  12. package/dist/chunk-HJ2EIZ4S.js.map +1 -0
  13. package/dist/{chunk-G7XDUN3Z.js → chunk-I2YGB7Z6.js} +24 -44
  14. package/dist/chunk-I2YGB7Z6.js.map +1 -0
  15. package/dist/chunk-LIUE7M7K.js +72 -0
  16. package/dist/chunk-LIUE7M7K.js.map +1 -0
  17. package/dist/{chunk-YNDCD53D.js → chunk-QHB7LGCA.js} +123 -16
  18. package/dist/chunk-QHB7LGCA.js.map +1 -0
  19. package/dist/chunk-R4MDAYFO.js +642 -0
  20. package/dist/chunk-R4MDAYFO.js.map +1 -0
  21. package/dist/cms/index.js +4 -2
  22. package/dist/cms/index.js.map +1 -1
  23. package/dist/cron/index.d.ts +32 -0
  24. package/dist/cron/index.js +63 -0
  25. package/dist/cron/index.js.map +1 -0
  26. package/dist/database/index.d.ts +37 -0
  27. package/dist/database/index.js +32 -0
  28. package/dist/database/index.js.map +1 -0
  29. package/dist/email/index.d.ts +29 -0
  30. package/dist/email/index.js +60 -0
  31. package/dist/email/index.js.map +1 -0
  32. package/dist/errors/index.js.map +1 -1
  33. package/dist/index.d.ts +176 -3
  34. package/dist/index.js +270 -6
  35. package/dist/index.js.map +1 -1
  36. package/dist/notifications/index.d.ts +35 -1
  37. package/dist/notifications/index.js +61 -4
  38. package/dist/notifications/index.js.map +1 -1
  39. package/dist/payments/index.d.ts +11 -3
  40. package/dist/payments/index.js +101 -7
  41. package/dist/payments/index.js.map +1 -1
  42. package/dist/roles/index.js +6 -4
  43. package/dist/roles/index.js.map +1 -1
  44. package/dist/seo/index.js.map +1 -1
  45. package/dist/server/index.js.map +1 -1
  46. package/dist/storage/index.d.ts +1 -1
  47. package/dist/storage/index.js +18 -9
  48. package/dist/storage/index.js.map +1 -1
  49. package/dist/{types-DtY5lp3P.d.ts → types-1uP3V_pe.d.ts} +5 -0
  50. package/package.json +120 -105
  51. package/dist/chunk-5XIZHBKE.js.map +0 -1
  52. package/dist/chunk-G7XDUN3Z.js.map +0 -1
  53. package/dist/chunk-YNDCD53D.js.map +0 -1
@@ -0,0 +1,167 @@
1
+ import * as react_jsx_runtime from 'react/jsx-runtime';
2
+ import { ReactNode } from 'react';
3
+ import { SupabaseClient } from '@supabase/supabase-js';
4
+
5
+ interface DatabaseResult<T = Record<string, unknown>> {
6
+ success: boolean;
7
+ data: T[];
8
+ rowCount: number;
9
+ error?: string;
10
+ schema?: string;
11
+ }
12
+ interface SingleResult<T = Record<string, unknown>> {
13
+ success: boolean;
14
+ data: T | null;
15
+ error?: string;
16
+ }
17
+ interface MutationResult {
18
+ success: boolean;
19
+ rowCount: number;
20
+ error?: string;
21
+ schema?: string;
22
+ executed_sql?: string;
23
+ }
24
+ interface ColumnInfo {
25
+ name: string;
26
+ type: string;
27
+ nullable: boolean;
28
+ default: string | null;
29
+ ordinal: number;
30
+ }
31
+ interface IndexInfo {
32
+ name: string;
33
+ definition: string;
34
+ is_unique: boolean;
35
+ is_primary: boolean;
36
+ }
37
+ interface ForeignKeyInfo {
38
+ name: string;
39
+ column: string;
40
+ references_table: string;
41
+ references_column: string;
42
+ }
43
+ interface PolicyInfo {
44
+ name: string;
45
+ command: string;
46
+ permissive: boolean;
47
+ roles: string[];
48
+ }
49
+ interface TableInfo {
50
+ name: string;
51
+ columns: ColumnInfo[];
52
+ rowCount: number;
53
+ indexes: IndexInfo[];
54
+ foreignKeys: ForeignKeyInfo[];
55
+ rlsPolicies: PolicyInfo[];
56
+ }
57
+ interface SchemaInfo {
58
+ exists: boolean;
59
+ schema?: string;
60
+ tables: TableInfo[];
61
+ tablesCount: number;
62
+ createdAt?: string;
63
+ lastAccessedAt?: string;
64
+ }
65
+ interface OrderOption {
66
+ ascending?: boolean;
67
+ nullsFirst?: boolean;
68
+ }
69
+ type FilterValue = string | number | boolean | null;
70
+
71
+ interface ServerProxy {
72
+ serverQuery: (sql: string) => Promise<{
73
+ success: boolean;
74
+ data?: unknown[];
75
+ rowCount?: number;
76
+ error?: string;
77
+ schema?: string;
78
+ }>;
79
+ serverExec: (sql: string) => Promise<{
80
+ success: boolean;
81
+ data?: unknown[];
82
+ rowCount?: number;
83
+ error?: string;
84
+ schema?: string;
85
+ }>;
86
+ }
87
+ declare class QueryBuilder<T = Record<string, unknown>> {
88
+ private readonly supabase;
89
+ private readonly projectId;
90
+ private readonly table;
91
+ private readonly serverProxy?;
92
+ private operation;
93
+ private selectColumns;
94
+ private filters;
95
+ private orderClauses;
96
+ private limitValue;
97
+ private offsetValue;
98
+ private insertData;
99
+ private updateData;
100
+ private upsertConflict;
101
+ private singleMode;
102
+ private maybeSingleMode;
103
+ constructor(supabase: SupabaseClient, projectId: string, table: string, serverProxy?: ServerProxy);
104
+ select(columns?: string): this;
105
+ eq(column: string, value: FilterValue): this;
106
+ neq(column: string, value: FilterValue): this;
107
+ gt(column: string, value: FilterValue): this;
108
+ lt(column: string, value: FilterValue): this;
109
+ gte(column: string, value: FilterValue): this;
110
+ lte(column: string, value: FilterValue): this;
111
+ like(column: string, pattern: string): this;
112
+ ilike(column: string, pattern: string): this;
113
+ in(column: string, values: FilterValue[]): this;
114
+ is(column: string, value: null | boolean): this;
115
+ order(column: string, options?: OrderOption): this;
116
+ limit(count: number): this;
117
+ offset(count: number): this;
118
+ insert(records: Record<string, FilterValue> | Record<string, FilterValue>[]): this;
119
+ update(values: Record<string, FilterValue>): this;
120
+ delete(): this;
121
+ upsert(records: Record<string, FilterValue> | Record<string, FilterValue>[], options?: {
122
+ onConflict?: string;
123
+ }): this;
124
+ count(): QueryBuilder<{
125
+ count: number;
126
+ }>;
127
+ single(): QueryBuilder<T>;
128
+ maybeSingle(): QueryBuilder<T>;
129
+ private buildWhereClause;
130
+ private buildSelectSql;
131
+ private buildCountSql;
132
+ private buildInsertSql;
133
+ private buildUpsertSql;
134
+ private buildUpdateSql;
135
+ private buildDeleteSql;
136
+ private executeQuery;
137
+ then<TResult1 = DatabaseResult<T> | SingleResult<T>, TResult2 = never>(onfulfilled?: ((value: DatabaseResult<T> | SingleResult<T>) => TResult1 | PromiseLike<TResult1>) | null, onrejected?: ((reason: unknown) => TResult2 | PromiseLike<TResult2>) | null): Promise<TResult1 | TResult2>;
138
+ }
139
+
140
+ declare class DatabaseClient {
141
+ private readonly supabase;
142
+ private readonly projectId;
143
+ private apiKey?;
144
+ private platformUrl?;
145
+ private serverMode;
146
+ constructor(supabase: SupabaseClient | null, projectId: string);
147
+ static createServerClient(projectId: string, apiKey: string, platformUrl?: string): DatabaseClient;
148
+ from<T = Record<string, unknown>>(table: string): QueryBuilder<T>;
149
+ sql<T = Record<string, unknown>>(query: string): Promise<DatabaseResult<T>>;
150
+ execute(sql: string): Promise<MutationResult>;
151
+ getSchema(): Promise<SchemaInfo>;
152
+ private _serverRequest;
153
+ private _serverQuery;
154
+ private _serverExecute;
155
+ private _serverGetSchema;
156
+ }
157
+
158
+ interface DatabaseProviderProps {
159
+ children: ReactNode;
160
+ projectId?: string;
161
+ }
162
+ declare function DatabaseProvider({ children, projectId }: DatabaseProviderProps): react_jsx_runtime.JSX.Element;
163
+ declare function useDatabase(): DatabaseClient;
164
+ declare function useDatabaseOptional(): DatabaseClient | null;
165
+ declare function useIsDatabaseConfigured(): boolean;
166
+
167
+ export { type ColumnInfo as C, DatabaseClient as D, type FilterValue as F, type IndexInfo as I, type MutationResult as M, type OrderOption as O, type PolicyInfo as P, QueryBuilder as Q, type SchemaInfo as S, type TableInfo as T, DatabaseProvider as a, type DatabaseResult as b, type ForeignKeyInfo as c, type SingleResult as d, useDatabaseOptional as e, useIsDatabaseConfigured as f, useDatabase as u };
@@ -15,4 +15,25 @@ interface UseAnalyticsReturn {
15
15
  }
16
16
  declare function useAnalytics(): UseAnalyticsReturn;
17
17
 
18
- export { useAnalytics };
18
+ interface MetricResult<T = Record<string, unknown>> {
19
+ data: T | null;
20
+ error: string | null;
21
+ }
22
+ interface UseMetricsReturn {
23
+ getTotalUsers: () => Promise<MetricResult<{
24
+ count: number;
25
+ }>>;
26
+ getUserGrowth: (days?: number) => Promise<MetricResult<Array<{
27
+ date: string;
28
+ count: number;
29
+ }>>>;
30
+ getActiveUsers: (days?: number) => Promise<MetricResult<{
31
+ count: number;
32
+ }>>;
33
+ getRecentActivity: (limit?: number) => Promise<MetricResult<Array<Record<string, unknown>>>>;
34
+ runQuery: <T = Record<string, unknown>>(sql: string) => Promise<MetricResult<T>>;
35
+ isConfigured: boolean;
36
+ }
37
+ declare function useMetrics(): UseMetricsReturn;
38
+
39
+ export { useAnalytics, useMetrics };
@@ -1,13 +1,18 @@
1
1
  import {
2
2
  AuthContext
3
- } from "../chunk-YNDCD53D.js";
3
+ } from "../chunk-QHB7LGCA.js";
4
4
  import {
5
5
  ezcoder,
6
6
  ezcoderAuthIntegration
7
- } from "../chunk-5XIZHBKE.js";
7
+ } from "../chunk-HJ2EIZ4S.js";
8
8
  import {
9
+ isSupabaseConfigured,
10
+ supabase
11
+ } from "../chunk-I2YGB7Z6.js";
12
+ import {
13
+ env,
9
14
  features
10
- } from "../chunk-G7XDUN3Z.js";
15
+ } from "../chunk-LIUE7M7K.js";
11
16
 
12
17
  // src/analytics/useAnalytics.ts
13
18
  import { useEffect, useRef, useCallback, useContext } from "react";
@@ -70,7 +75,77 @@ function useAnalytics() {
70
75
  isConfigured: features.analytics
71
76
  };
72
77
  }
78
+
79
+ // src/analytics/useMetrics.ts
80
+ import { useCallback as useCallback2, useMemo } from "react";
81
+ async function queryRpc(sql, projectId) {
82
+ const { data, error } = await supabase.rpc("sdk_query_project", {
83
+ p_project_id: projectId,
84
+ p_sql: sql
85
+ });
86
+ if (error) {
87
+ return { data: null, error: error.message };
88
+ }
89
+ const result = data;
90
+ if (!result?.success) {
91
+ return { data: null, error: result?.error || "Query failed" };
92
+ }
93
+ return { data: result.data, error: null };
94
+ }
95
+ function useMetrics() {
96
+ const projectId = env.EZC_PROJECT_ID;
97
+ const configured = isSupabaseConfigured && Boolean(projectId);
98
+ const getTotalUsers = useCallback2(async () => {
99
+ if (!configured || !projectId) return { data: null, error: "Not configured" };
100
+ const result = await queryRpc(
101
+ "SELECT COUNT(*)::integer as count FROM user_profiles",
102
+ projectId
103
+ );
104
+ return {
105
+ data: result.data?.[0] ?? null,
106
+ error: result.error
107
+ };
108
+ }, [configured, projectId]);
109
+ const getUserGrowth = useCallback2(async (days = 30) => {
110
+ if (!configured || !projectId) return { data: null, error: "Not configured" };
111
+ return queryRpc(
112
+ `SELECT date_trunc('day', created_at)::date::text as date, COUNT(*)::integer as count FROM user_profiles WHERE created_at > NOW() - INTERVAL '${days} days' GROUP BY 1 ORDER BY 1`,
113
+ projectId
114
+ );
115
+ }, [configured, projectId]);
116
+ const getActiveUsers = useCallback2(async (days = 7) => {
117
+ if (!configured || !projectId) return { data: null, error: "Not configured" };
118
+ const result = await queryRpc(
119
+ `SELECT COUNT(DISTINCT user_id)::integer as count FROM activity_log WHERE created_at > NOW() - INTERVAL '${days} days'`,
120
+ projectId
121
+ );
122
+ return {
123
+ data: result.data?.[0] ?? null,
124
+ error: result.error
125
+ };
126
+ }, [configured, projectId]);
127
+ const getRecentActivity = useCallback2(async (limit = 20) => {
128
+ if (!configured || !projectId) return { data: null, error: "Not configured" };
129
+ return queryRpc(
130
+ `SELECT * FROM activity_log ORDER BY created_at DESC LIMIT ${limit}`,
131
+ projectId
132
+ );
133
+ }, [configured, projectId]);
134
+ const runQuery = useCallback2(async (sql) => {
135
+ if (!configured || !projectId) return { data: null, error: "Not configured" };
136
+ return queryRpc(sql, projectId);
137
+ }, [configured, projectId]);
138
+ return useMemo(() => ({
139
+ getTotalUsers,
140
+ getUserGrowth,
141
+ getActiveUsers,
142
+ getRecentActivity,
143
+ runQuery,
144
+ isConfigured: configured
145
+ }), [getTotalUsers, getUserGrowth, getActiveUsers, getRecentActivity, runQuery, configured]);
146
+ }
73
147
  export {
74
- useAnalytics
148
+ useAnalytics,
149
+ useMetrics
75
150
  };
76
151
  //# sourceMappingURL=index.js.map
@@ -1 +1 @@
1
- {"version":3,"sources":["../../src/analytics/useAnalytics.ts"],"sourcesContent":["import { useEffect, useRef, useCallback, useContext } from 'react';\nimport { ezcoder, ezcoderAuthIntegration } from '../core/platform';\nimport { features } from '../core/config';\nimport { AuthContext } from '../auth/AuthProvider';\n\ninterface UseAnalyticsReturn {\n trackEvent: (eventName: string, properties?: Record<string, unknown>) => void;\n trackPageView: (pathname?: string) => void;\n trackError: (message: string, context?: Record<string, unknown>) => void;\n identify: (userId: string, traits?: Record<string, unknown>) => void;\n trackSignup: (user: { id?: string; email?: string }) => void;\n trackLogin: (user: { id?: string }) => void;\n trackLogout: (userId: string) => void;\n isConfigured: boolean;\n}\n\nexport function useAnalytics(): UseAnalyticsReturn {\n const auth = useContext(AuthContext);\n const lastPageViewRef = useRef<string>('');\n\n const enrichProperties = useCallback((properties: Record<string, unknown> = {}): Record<string, unknown> => {\n const enriched = { ...properties };\n if (auth?.user?.id) {\n enriched.userId = auth.user.id;\n enriched.userEmail = auth.user.email;\n }\n if (auth?.profile) {\n const profile = auth.profile as unknown as Record<string, unknown>;\n enriched.userTier = profile.subscription_tier || 'free';\n enriched.userName = profile.display_name;\n }\n return enriched;\n }, [auth?.user, auth?.profile]);\n\n const trackEvent = useCallback((eventName: string, properties: Record<string, unknown> = {}) => {\n if (!features.analytics) return;\n ezcoder.analytics.track(eventName, enrichProperties(properties));\n }, [enrichProperties]);\n\n const trackPageView = useCallback((pathname?: string) => {\n if (!features.analytics) return;\n const path = pathname || (typeof window !== 'undefined' ? window.location.pathname : '/');\n if (path === lastPageViewRef.current) return;\n lastPageViewRef.current = path;\n ezcoder.analytics.pageView(path);\n }, []);\n\n const trackError = useCallback((message: string, context: Record<string, unknown> = {}) => {\n if (!features.analytics) return;\n ezcoder.analytics.error(message, enrichProperties(context));\n }, [enrichProperties]);\n\n const identify = useCallback((userId: string, traits: Record<string, unknown> = {}) => {\n if (!features.analytics) return;\n ezcoder.analytics.identify(userId, traits);\n }, []);\n\n const trackSignup = useCallback((user: { id?: string; email?: string }) => {\n ezcoderAuthIntegration.onSignup(user);\n }, []);\n\n const trackLogin = useCallback((user: { id?: string }) => {\n ezcoderAuthIntegration.onLogin(user);\n }, []);\n\n const trackLogout = useCallback((userId: string) => {\n ezcoderAuthIntegration.onLogout(userId);\n }, []);\n\n useEffect(() => {\n if (!features.analytics) return;\n trackPageView();\n }, [trackPageView]);\n\n return {\n trackEvent,\n trackPageView,\n trackError,\n identify,\n trackSignup,\n trackLogin,\n trackLogout,\n isConfigured: features.analytics,\n };\n}\n"],"mappings":";;;;;;;;;;;;AAAA,SAAS,WAAW,QAAQ,aAAa,kBAAkB;AAgBpD,SAAS,eAAmC;AACjD,QAAM,OAAO,WAAW,WAAW;AACnC,QAAM,kBAAkB,OAAe,EAAE;AAEzC,QAAM,mBAAmB,YAAY,CAAC,aAAsC,CAAC,MAA+B;AAC1G,UAAM,WAAW,EAAE,GAAG,WAAW;AACjC,QAAI,MAAM,MAAM,IAAI;AAClB,eAAS,SAAS,KAAK,KAAK;AAC5B,eAAS,YAAY,KAAK,KAAK;AAAA,IACjC;AACA,QAAI,MAAM,SAAS;AACjB,YAAM,UAAU,KAAK;AACrB,eAAS,WAAW,QAAQ,qBAAqB;AACjD,eAAS,WAAW,QAAQ;AAAA,IAC9B;AACA,WAAO;AAAA,EACT,GAAG,CAAC,MAAM,MAAM,MAAM,OAAO,CAAC;AAE9B,QAAM,aAAa,YAAY,CAAC,WAAmB,aAAsC,CAAC,MAAM;AAC9F,QAAI,CAAC,SAAS,UAAW;AACzB,YAAQ,UAAU,MAAM,WAAW,iBAAiB,UAAU,CAAC;AAAA,EACjE,GAAG,CAAC,gBAAgB,CAAC;AAErB,QAAM,gBAAgB,YAAY,CAAC,aAAsB;AACvD,QAAI,CAAC,SAAS,UAAW;AACzB,UAAM,OAAO,aAAa,OAAO,WAAW,cAAc,OAAO,SAAS,WAAW;AACrF,QAAI,SAAS,gBAAgB,QAAS;AACtC,oBAAgB,UAAU;AAC1B,YAAQ,UAAU,SAAS,IAAI;AAAA,EACjC,GAAG,CAAC,CAAC;AAEL,QAAM,aAAa,YAAY,CAAC,SAAiB,UAAmC,CAAC,MAAM;AACzF,QAAI,CAAC,SAAS,UAAW;AACzB,YAAQ,UAAU,MAAM,SAAS,iBAAiB,OAAO,CAAC;AAAA,EAC5D,GAAG,CAAC,gBAAgB,CAAC;AAErB,QAAM,WAAW,YAAY,CAAC,QAAgB,SAAkC,CAAC,MAAM;AACrF,QAAI,CAAC,SAAS,UAAW;AACzB,YAAQ,UAAU,SAAS,QAAQ,MAAM;AAAA,EAC3C,GAAG,CAAC,CAAC;AAEL,QAAM,cAAc,YAAY,CAAC,SAA0C;AACzE,2BAAuB,SAAS,IAAI;AAAA,EACtC,GAAG,CAAC,CAAC;AAEL,QAAM,aAAa,YAAY,CAAC,SAA0B;AACxD,2BAAuB,QAAQ,IAAI;AAAA,EACrC,GAAG,CAAC,CAAC;AAEL,QAAM,cAAc,YAAY,CAAC,WAAmB;AAClD,2BAAuB,SAAS,MAAM;AAAA,EACxC,GAAG,CAAC,CAAC;AAEL,YAAU,MAAM;AACd,QAAI,CAAC,SAAS,UAAW;AACzB,kBAAc;AAAA,EAChB,GAAG,CAAC,aAAa,CAAC;AAElB,SAAO;AAAA,IACL;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA,cAAc,SAAS;AAAA,EACzB;AACF;","names":[]}
1
+ {"version":3,"sources":["../../src/analytics/useAnalytics.ts","../../src/analytics/useMetrics.ts"],"sourcesContent":["import { useEffect, useRef, useCallback, useContext } from 'react';\r\nimport { ezcoder, ezcoderAuthIntegration } from '../core/platform';\r\nimport { features } from '../core/config';\r\nimport { AuthContext } from '../auth/AuthProvider';\r\n\r\ninterface UseAnalyticsReturn {\r\n trackEvent: (eventName: string, properties?: Record<string, unknown>) => void;\r\n trackPageView: (pathname?: string) => void;\r\n trackError: (message: string, context?: Record<string, unknown>) => void;\r\n identify: (userId: string, traits?: Record<string, unknown>) => void;\r\n trackSignup: (user: { id?: string; email?: string }) => void;\r\n trackLogin: (user: { id?: string }) => void;\r\n trackLogout: (userId: string) => void;\r\n isConfigured: boolean;\r\n}\r\n\r\nexport function useAnalytics(): UseAnalyticsReturn {\r\n const auth = useContext(AuthContext);\r\n const lastPageViewRef = useRef<string>('');\r\n\r\n const enrichProperties = useCallback((properties: Record<string, unknown> = {}): Record<string, unknown> => {\r\n const enriched = { ...properties };\r\n if (auth?.user?.id) {\r\n enriched.userId = auth.user.id;\r\n enriched.userEmail = auth.user.email;\r\n }\r\n if (auth?.profile) {\r\n const profile = auth.profile as unknown as Record<string, unknown>;\r\n enriched.userTier = profile.subscription_tier || 'free';\r\n enriched.userName = profile.display_name;\r\n }\r\n return enriched;\r\n }, [auth?.user, auth?.profile]);\r\n\r\n const trackEvent = useCallback((eventName: string, properties: Record<string, unknown> = {}) => {\r\n if (!features.analytics) return;\r\n ezcoder.analytics.track(eventName, enrichProperties(properties));\r\n }, [enrichProperties]);\r\n\r\n const trackPageView = useCallback((pathname?: string) => {\r\n if (!features.analytics) return;\r\n const path = pathname || (typeof window !== 'undefined' ? window.location.pathname : '/');\r\n if (path === lastPageViewRef.current) return;\r\n lastPageViewRef.current = path;\r\n ezcoder.analytics.pageView(path);\r\n }, []);\r\n\r\n const trackError = useCallback((message: string, context: Record<string, unknown> = {}) => {\r\n if (!features.analytics) return;\r\n ezcoder.analytics.error(message, enrichProperties(context));\r\n }, [enrichProperties]);\r\n\r\n const identify = useCallback((userId: string, traits: Record<string, unknown> = {}) => {\r\n if (!features.analytics) return;\r\n ezcoder.analytics.identify(userId, traits);\r\n }, []);\r\n\r\n const trackSignup = useCallback((user: { id?: string; email?: string }) => {\r\n ezcoderAuthIntegration.onSignup(user);\r\n }, []);\r\n\r\n const trackLogin = useCallback((user: { id?: string }) => {\r\n ezcoderAuthIntegration.onLogin(user);\r\n }, []);\r\n\r\n const trackLogout = useCallback((userId: string) => {\r\n ezcoderAuthIntegration.onLogout(userId);\r\n }, []);\r\n\r\n useEffect(() => {\r\n if (!features.analytics) return;\r\n trackPageView();\r\n }, [trackPageView]);\r\n\r\n return {\r\n trackEvent,\r\n trackPageView,\r\n trackError,\r\n identify,\r\n trackSignup,\r\n trackLogin,\r\n trackLogout,\r\n isConfigured: features.analytics,\r\n };\r\n}\r\n","import { useCallback, useMemo } from 'react';\r\nimport { supabase, isSupabaseConfigured } from '../core/supabase';\r\nimport { env } from '../core/config';\r\n\r\ninterface MetricResult<T = Record<string, unknown>> {\r\n data: T | null;\r\n error: string | null;\r\n}\r\n\r\ninterface UseMetricsReturn {\r\n getTotalUsers: () => Promise<MetricResult<{ count: number }>>;\r\n getUserGrowth: (days?: number) => Promise<MetricResult<Array<{ date: string; count: number }>>>;\r\n getActiveUsers: (days?: number) => Promise<MetricResult<{ count: number }>>;\r\n getRecentActivity: (limit?: number) => Promise<MetricResult<Array<Record<string, unknown>>>>;\r\n runQuery: <T = Record<string, unknown>>(sql: string) => Promise<MetricResult<T>>;\r\n isConfigured: boolean;\r\n}\r\n\r\nasync function queryRpc<T>(sql: string, projectId: string): Promise<MetricResult<T>> {\r\n const { data, error } = await supabase.rpc('sdk_query_project', {\r\n p_project_id: projectId,\r\n p_sql: sql,\r\n });\r\n\r\n if (error) {\r\n return { data: null, error: error.message };\r\n }\r\n\r\n const result = data as { success: boolean; data: T; error?: string };\r\n if (!result?.success) {\r\n return { data: null, error: result?.error || 'Query failed' };\r\n }\r\n\r\n return { data: result.data, error: null };\r\n}\r\n\r\nexport function useMetrics(): UseMetricsReturn {\r\n const projectId = env.EZC_PROJECT_ID;\r\n const configured = isSupabaseConfigured && Boolean(projectId);\r\n\r\n const getTotalUsers = useCallback(async () => {\r\n if (!configured || !projectId) return { data: null, error: 'Not configured' };\r\n const result = await queryRpc<Array<{ count: number }>>(\r\n 'SELECT COUNT(*)::integer as count FROM user_profiles',\r\n projectId,\r\n );\r\n return {\r\n data: result.data?.[0] ?? null,\r\n error: result.error,\r\n };\r\n }, [configured, projectId]);\r\n\r\n const getUserGrowth = useCallback(async (days = 30) => {\r\n if (!configured || !projectId) return { data: null, error: 'Not configured' };\r\n return queryRpc<Array<{ date: string; count: number }>>(\r\n `SELECT date_trunc('day', created_at)::date::text as date, COUNT(*)::integer as count FROM user_profiles WHERE created_at > NOW() - INTERVAL '${days} days' GROUP BY 1 ORDER BY 1`,\r\n projectId,\r\n );\r\n }, [configured, projectId]);\r\n\r\n const getActiveUsers = useCallback(async (days = 7) => {\r\n if (!configured || !projectId) return { data: null, error: 'Not configured' };\r\n const result = await queryRpc<Array<{ count: number }>>(\r\n `SELECT COUNT(DISTINCT user_id)::integer as count FROM activity_log WHERE created_at > NOW() - INTERVAL '${days} days'`,\r\n projectId,\r\n );\r\n return {\r\n data: result.data?.[0] ?? null,\r\n error: result.error,\r\n };\r\n }, [configured, projectId]);\r\n\r\n const getRecentActivity = useCallback(async (limit = 20) => {\r\n if (!configured || !projectId) return { data: null, error: 'Not configured' };\r\n return queryRpc<Array<Record<string, unknown>>>(\r\n `SELECT * FROM activity_log ORDER BY created_at DESC LIMIT ${limit}`,\r\n projectId,\r\n );\r\n }, [configured, projectId]);\r\n\r\n const runQuery = useCallback(async <T = Record<string, unknown>>(sql: string) => {\r\n if (!configured || !projectId) return { data: null, error: 'Not configured' } as MetricResult<T>;\r\n return queryRpc<T>(sql, projectId);\r\n }, [configured, projectId]);\r\n\r\n return useMemo(() => ({\r\n getTotalUsers,\r\n getUserGrowth,\r\n getActiveUsers,\r\n getRecentActivity,\r\n runQuery,\r\n isConfigured: configured,\r\n }), [getTotalUsers, getUserGrowth, getActiveUsers, getRecentActivity, runQuery, configured]);\r\n}\r\n"],"mappings":"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","names":["useCallback","useCallback"]}
@@ -1 +1 @@
1
- {"version":3,"sources":["../../src/animation/variants.ts"],"sourcesContent":["export const DURATION = {\n fast: 0.15,\n normal: 0.3,\n slow: 0.5,\n};\n\nexport const EASING = {\n easeInOut: [0.4, 0, 0.2, 1] as const,\n easeOut: [0, 0, 0.2, 1] as const,\n spring: { type: 'spring' as const, stiffness: 300, damping: 30 },\n};\n\nexport const fadeIn = {\n initial: { opacity: 0 },\n animate: { opacity: 1 },\n exit: { opacity: 0 },\n transition: { duration: DURATION.normal },\n};\n\nexport const slideUp = {\n initial: { opacity: 0, y: 20 },\n animate: { opacity: 1, y: 0 },\n exit: { opacity: 0, y: -20 },\n transition: { duration: DURATION.normal },\n};\n\nexport const slideInLeft = {\n initial: { opacity: 0, x: -20 },\n animate: { opacity: 1, x: 0 },\n exit: { opacity: 0, x: 20 },\n transition: { duration: DURATION.normal },\n};\n\nexport const scaleIn = {\n initial: { opacity: 0, scale: 0.95 },\n animate: { opacity: 1, scale: 1 },\n exit: { opacity: 0, scale: 0.95 },\n transition: { duration: DURATION.fast },\n};\n\nexport const staggerContainer = {\n animate: {\n transition: {\n staggerChildren: 0.1,\n },\n },\n};\n\nexport const staggerItem = {\n initial: { opacity: 0, y: 10 },\n animate: { opacity: 1, y: 0 },\n};\n\nexport const pageTransition = {\n initial: { opacity: 0, y: 10 },\n animate: { opacity: 1, y: 0 },\n exit: { opacity: 0, y: -10 },\n transition: { duration: DURATION.normal },\n};\n\nexport const tailwindAnimations = {\n keyframes: {\n fadeIn: { '0%': { opacity: '0' }, '100%': { opacity: '1' } },\n slideUp: { '0%': { opacity: '0', transform: 'translateY(10px)' }, '100%': { opacity: '1', transform: 'translateY(0)' } },\n slideDown: { '0%': { opacity: '0', transform: 'translateY(-10px)' }, '100%': { opacity: '1', transform: 'translateY(0)' } },\n scaleIn: { '0%': { opacity: '0', transform: 'scale(0.95)' }, '100%': { opacity: '1', transform: 'scale(1)' } },\n shimmer: { '0%': { backgroundPosition: '-200% 0' }, '100%': { backgroundPosition: '200% 0' } },\n },\n animation: {\n 'fade-in': 'fadeIn 0.3s ease-out',\n 'slide-up': 'slideUp 0.3s ease-out',\n 'slide-down': 'slideDown 0.3s ease-out',\n 'scale-in': 'scaleIn 0.2s ease-out',\n shimmer: 'shimmer 2s infinite linear',\n },\n};\n"],"mappings":";AAAO,IAAM,WAAW;AAAA,EACtB,MAAM;AAAA,EACN,QAAQ;AAAA,EACR,MAAM;AACR;AAEO,IAAM,SAAS;AAAA,EACpB,WAAW,CAAC,KAAK,GAAG,KAAK,CAAC;AAAA,EAC1B,SAAS,CAAC,GAAG,GAAG,KAAK,CAAC;AAAA,EACtB,QAAQ,EAAE,MAAM,UAAmB,WAAW,KAAK,SAAS,GAAG;AACjE;AAEO,IAAM,SAAS;AAAA,EACpB,SAAS,EAAE,SAAS,EAAE;AAAA,EACtB,SAAS,EAAE,SAAS,EAAE;AAAA,EACtB,MAAM,EAAE,SAAS,EAAE;AAAA,EACnB,YAAY,EAAE,UAAU,SAAS,OAAO;AAC1C;AAEO,IAAM,UAAU;AAAA,EACrB,SAAS,EAAE,SAAS,GAAG,GAAG,GAAG;AAAA,EAC7B,SAAS,EAAE,SAAS,GAAG,GAAG,EAAE;AAAA,EAC5B,MAAM,EAAE,SAAS,GAAG,GAAG,IAAI;AAAA,EAC3B,YAAY,EAAE,UAAU,SAAS,OAAO;AAC1C;AAEO,IAAM,cAAc;AAAA,EACzB,SAAS,EAAE,SAAS,GAAG,GAAG,IAAI;AAAA,EAC9B,SAAS,EAAE,SAAS,GAAG,GAAG,EAAE;AAAA,EAC5B,MAAM,EAAE,SAAS,GAAG,GAAG,GAAG;AAAA,EAC1B,YAAY,EAAE,UAAU,SAAS,OAAO;AAC1C;AAEO,IAAM,UAAU;AAAA,EACrB,SAAS,EAAE,SAAS,GAAG,OAAO,KAAK;AAAA,EACnC,SAAS,EAAE,SAAS,GAAG,OAAO,EAAE;AAAA,EAChC,MAAM,EAAE,SAAS,GAAG,OAAO,KAAK;AAAA,EAChC,YAAY,EAAE,UAAU,SAAS,KAAK;AACxC;AAEO,IAAM,mBAAmB;AAAA,EAC9B,SAAS;AAAA,IACP,YAAY;AAAA,MACV,iBAAiB;AAAA,IACnB;AAAA,EACF;AACF;AAEO,IAAM,cAAc;AAAA,EACzB,SAAS,EAAE,SAAS,GAAG,GAAG,GAAG;AAAA,EAC7B,SAAS,EAAE,SAAS,GAAG,GAAG,EAAE;AAC9B;AAEO,IAAM,iBAAiB;AAAA,EAC5B,SAAS,EAAE,SAAS,GAAG,GAAG,GAAG;AAAA,EAC7B,SAAS,EAAE,SAAS,GAAG,GAAG,EAAE;AAAA,EAC5B,MAAM,EAAE,SAAS,GAAG,GAAG,IAAI;AAAA,EAC3B,YAAY,EAAE,UAAU,SAAS,OAAO;AAC1C;AAEO,IAAM,qBAAqB;AAAA,EAChC,WAAW;AAAA,IACT,QAAQ,EAAE,MAAM,EAAE,SAAS,IAAI,GAAG,QAAQ,EAAE,SAAS,IAAI,EAAE;AAAA,IAC3D,SAAS,EAAE,MAAM,EAAE,SAAS,KAAK,WAAW,mBAAmB,GAAG,QAAQ,EAAE,SAAS,KAAK,WAAW,gBAAgB,EAAE;AAAA,IACvH,WAAW,EAAE,MAAM,EAAE,SAAS,KAAK,WAAW,oBAAoB,GAAG,QAAQ,EAAE,SAAS,KAAK,WAAW,gBAAgB,EAAE;AAAA,IAC1H,SAAS,EAAE,MAAM,EAAE,SAAS,KAAK,WAAW,cAAc,GAAG,QAAQ,EAAE,SAAS,KAAK,WAAW,WAAW,EAAE;AAAA,IAC7G,SAAS,EAAE,MAAM,EAAE,oBAAoB,UAAU,GAAG,QAAQ,EAAE,oBAAoB,SAAS,EAAE;AAAA,EAC/F;AAAA,EACA,WAAW;AAAA,IACT,WAAW;AAAA,IACX,YAAY;AAAA,IACZ,cAAc;AAAA,IACd,YAAY;AAAA,IACZ,SAAS;AAAA,EACX;AACF;","names":[]}
1
+ {"version":3,"sources":["../../src/animation/variants.ts"],"sourcesContent":["export const DURATION = {\r\n fast: 0.15,\r\n normal: 0.3,\r\n slow: 0.5,\r\n};\r\n\r\nexport const EASING = {\r\n easeInOut: [0.4, 0, 0.2, 1] as const,\r\n easeOut: [0, 0, 0.2, 1] as const,\r\n spring: { type: 'spring' as const, stiffness: 300, damping: 30 },\r\n};\r\n\r\nexport const fadeIn = {\r\n initial: { opacity: 0 },\r\n animate: { opacity: 1 },\r\n exit: { opacity: 0 },\r\n transition: { duration: DURATION.normal },\r\n};\r\n\r\nexport const slideUp = {\r\n initial: { opacity: 0, y: 20 },\r\n animate: { opacity: 1, y: 0 },\r\n exit: { opacity: 0, y: -20 },\r\n transition: { duration: DURATION.normal },\r\n};\r\n\r\nexport const slideInLeft = {\r\n initial: { opacity: 0, x: -20 },\r\n animate: { opacity: 1, x: 0 },\r\n exit: { opacity: 0, x: 20 },\r\n transition: { duration: DURATION.normal },\r\n};\r\n\r\nexport const scaleIn = {\r\n initial: { opacity: 0, scale: 0.95 },\r\n animate: { opacity: 1, scale: 1 },\r\n exit: { opacity: 0, scale: 0.95 },\r\n transition: { duration: DURATION.fast },\r\n};\r\n\r\nexport const staggerContainer = {\r\n animate: {\r\n transition: {\r\n staggerChildren: 0.1,\r\n },\r\n },\r\n};\r\n\r\nexport const staggerItem = {\r\n initial: { opacity: 0, y: 10 },\r\n animate: { opacity: 1, y: 0 },\r\n};\r\n\r\nexport const pageTransition = {\r\n initial: { opacity: 0, y: 10 },\r\n animate: { opacity: 1, y: 0 },\r\n exit: { opacity: 0, y: -10 },\r\n transition: { duration: DURATION.normal },\r\n};\r\n\r\nexport const tailwindAnimations = {\r\n keyframes: {\r\n fadeIn: { '0%': { opacity: '0' }, '100%': { opacity: '1' } },\r\n slideUp: { '0%': { opacity: '0', transform: 'translateY(10px)' }, '100%': { opacity: '1', transform: 'translateY(0)' } },\r\n slideDown: { '0%': { opacity: '0', transform: 'translateY(-10px)' }, '100%': { opacity: '1', transform: 'translateY(0)' } },\r\n scaleIn: { '0%': { opacity: '0', transform: 'scale(0.95)' }, '100%': { opacity: '1', transform: 'scale(1)' } },\r\n shimmer: { '0%': { backgroundPosition: '-200% 0' }, '100%': { backgroundPosition: '200% 0' } },\r\n },\r\n animation: {\r\n 'fade-in': 'fadeIn 0.3s ease-out',\r\n 'slide-up': 'slideUp 0.3s ease-out',\r\n 'slide-down': 'slideDown 0.3s ease-out',\r\n 'scale-in': 'scaleIn 0.2s ease-out',\r\n shimmer: 'shimmer 2s infinite linear',\r\n },\r\n};\r\n"],"mappings":";AAAO,IAAM,WAAW;AAAA,EACtB,MAAM;AAAA,EACN,QAAQ;AAAA,EACR,MAAM;AACR;AAEO,IAAM,SAAS;AAAA,EACpB,WAAW,CAAC,KAAK,GAAG,KAAK,CAAC;AAAA,EAC1B,SAAS,CAAC,GAAG,GAAG,KAAK,CAAC;AAAA,EACtB,QAAQ,EAAE,MAAM,UAAmB,WAAW,KAAK,SAAS,GAAG;AACjE;AAEO,IAAM,SAAS;AAAA,EACpB,SAAS,EAAE,SAAS,EAAE;AAAA,EACtB,SAAS,EAAE,SAAS,EAAE;AAAA,EACtB,MAAM,EAAE,SAAS,EAAE;AAAA,EACnB,YAAY,EAAE,UAAU,SAAS,OAAO;AAC1C;AAEO,IAAM,UAAU;AAAA,EACrB,SAAS,EAAE,SAAS,GAAG,GAAG,GAAG;AAAA,EAC7B,SAAS,EAAE,SAAS,GAAG,GAAG,EAAE;AAAA,EAC5B,MAAM,EAAE,SAAS,GAAG,GAAG,IAAI;AAAA,EAC3B,YAAY,EAAE,UAAU,SAAS,OAAO;AAC1C;AAEO,IAAM,cAAc;AAAA,EACzB,SAAS,EAAE,SAAS,GAAG,GAAG,IAAI;AAAA,EAC9B,SAAS,EAAE,SAAS,GAAG,GAAG,EAAE;AAAA,EAC5B,MAAM,EAAE,SAAS,GAAG,GAAG,GAAG;AAAA,EAC1B,YAAY,EAAE,UAAU,SAAS,OAAO;AAC1C;AAEO,IAAM,UAAU;AAAA,EACrB,SAAS,EAAE,SAAS,GAAG,OAAO,KAAK;AAAA,EACnC,SAAS,EAAE,SAAS,GAAG,OAAO,EAAE;AAAA,EAChC,MAAM,EAAE,SAAS,GAAG,OAAO,KAAK;AAAA,EAChC,YAAY,EAAE,UAAU,SAAS,KAAK;AACxC;AAEO,IAAM,mBAAmB;AAAA,EAC9B,SAAS;AAAA,IACP,YAAY;AAAA,MACV,iBAAiB;AAAA,IACnB;AAAA,EACF;AACF;AAEO,IAAM,cAAc;AAAA,EACzB,SAAS,EAAE,SAAS,GAAG,GAAG,GAAG;AAAA,EAC7B,SAAS,EAAE,SAAS,GAAG,GAAG,EAAE;AAC9B;AAEO,IAAM,iBAAiB;AAAA,EAC5B,SAAS,EAAE,SAAS,GAAG,GAAG,GAAG;AAAA,EAC7B,SAAS,EAAE,SAAS,GAAG,GAAG,EAAE;AAAA,EAC5B,MAAM,EAAE,SAAS,GAAG,GAAG,IAAI;AAAA,EAC3B,YAAY,EAAE,UAAU,SAAS,OAAO;AAC1C;AAEO,IAAM,qBAAqB;AAAA,EAChC,WAAW;AAAA,IACT,QAAQ,EAAE,MAAM,EAAE,SAAS,IAAI,GAAG,QAAQ,EAAE,SAAS,IAAI,EAAE;AAAA,IAC3D,SAAS,EAAE,MAAM,EAAE,SAAS,KAAK,WAAW,mBAAmB,GAAG,QAAQ,EAAE,SAAS,KAAK,WAAW,gBAAgB,EAAE;AAAA,IACvH,WAAW,EAAE,MAAM,EAAE,SAAS,KAAK,WAAW,oBAAoB,GAAG,QAAQ,EAAE,SAAS,KAAK,WAAW,gBAAgB,EAAE;AAAA,IAC1H,SAAS,EAAE,MAAM,EAAE,SAAS,KAAK,WAAW,cAAc,GAAG,QAAQ,EAAE,SAAS,KAAK,WAAW,WAAW,EAAE;AAAA,IAC7G,SAAS,EAAE,MAAM,EAAE,oBAAoB,UAAU,GAAG,QAAQ,EAAE,oBAAoB,SAAS,EAAE;AAAA,EAC/F;AAAA,EACA,WAAW;AAAA,IACT,WAAW;AAAA,IACX,YAAY;AAAA,IACZ,cAAc;AAAA,IACd,YAAY;AAAA,IACZ,SAAS;AAAA,EACX;AACF;","names":[]}
@@ -1,7 +1,7 @@
1
1
  import * as react_jsx_runtime from 'react/jsx-runtime';
2
2
  import * as react from 'react';
3
3
  import { User, Session } from '@supabase/supabase-js';
4
- import { U as UserProfile, e as SubscriptionTier } from '../types-DtY5lp3P.js';
4
+ import { U as UserProfile, e as SubscriptionTier } from '../types-1uP3V_pe.js';
5
5
 
6
6
  interface AuthResult<T = unknown> {
7
7
  data: T | null;
@@ -27,6 +27,7 @@ interface AuthContextType {
27
27
  error: Error | null;
28
28
  }>;
29
29
  resetPassword: (email: string) => Promise<AuthResult>;
30
+ updatePassword: (newPassword: string) => Promise<AuthResult>;
30
31
  updateProfile: (updates: Partial<UserProfile>) => Promise<AuthResult>;
31
32
  refetchProfile: (userId: string) => Promise<UserProfile | null>;
32
33
  }
@@ -2,11 +2,12 @@ import {
2
2
  AuthContext,
3
3
  AuthProvider,
4
4
  useAuth
5
- } from "../chunk-YNDCD53D.js";
6
- import "../chunk-5XIZHBKE.js";
5
+ } from "../chunk-QHB7LGCA.js";
6
+ import "../chunk-HJ2EIZ4S.js";
7
7
  import {
8
8
  supabase
9
- } from "../chunk-G7XDUN3Z.js";
9
+ } from "../chunk-I2YGB7Z6.js";
10
+ import "../chunk-LIUE7M7K.js";
10
11
 
11
12
  // src/auth/ProtectedRoute.tsx
12
13
  import { Fragment, jsx, jsxs } from "react/jsx-runtime";
@@ -429,9 +430,27 @@ function AuthCallback({ redirectTo = "/", loadingComponent }) {
429
430
  useEffect(() => {
430
431
  const handleCallback = async () => {
431
432
  try {
432
- const { error: error2 } = await supabase.auth.getSession();
433
- if (error2) {
434
- setError(error2.message);
433
+ let session = null;
434
+ const got = await supabase.auth.getSession();
435
+ if (got.error) {
436
+ setError(got.error.message);
437
+ return;
438
+ }
439
+ session = got.data?.session ?? null;
440
+ if (!session && typeof window !== "undefined" && new URLSearchParams(window.location.search).get("code")) {
441
+ const ex = await supabase.auth.exchangeCodeForSession(window.location.href);
442
+ if (ex.error) {
443
+ setError(ex.error.message);
444
+ return;
445
+ }
446
+ session = ex.data?.session ?? null;
447
+ }
448
+ if (typeof window !== "undefined" && window.opener && window.opener !== window) {
449
+ try {
450
+ window.opener.postMessage({ type: "ezc-auth-complete" }, "*");
451
+ } catch {
452
+ }
453
+ window.close();
435
454
  return;
436
455
  }
437
456
  window.location.href = redirectTo;
@@ -1 +1 @@
1
- {"version":3,"sources":["../../src/auth/ProtectedRoute.tsx","../../src/auth/LoginForm.tsx","../../src/auth/SignupForm.tsx","../../src/auth/ForgotPasswordForm.tsx","../../src/auth/AuthCallback.tsx"],"sourcesContent":["import { useAuth } from './AuthProvider';\nimport type { SubscriptionTier } from '../core/types';\n\ninterface ProtectedRouteProps {\n children: React.ReactNode;\n requiredRoles?: string[];\n requiredTier?: SubscriptionTier;\n fallback?: React.ReactNode;\n unauthorizedFallback?: React.ReactNode;\n allowUnconfigured?: boolean;\n loadingComponent?: React.ReactNode;\n loginPath?: string;\n}\n\nconst TIER_LEVELS: Record<string, number> = {\n free: 0,\n starter: 1,\n creator: 2,\n pro: 3,\n business: 4,\n enterprise: 5,\n};\n\nfunction DefaultLoadingSpinner() {\n return (\n <div style={{ display: 'flex', alignItems: 'center', justifyContent: 'center', minHeight: '200px' }}>\n <div style={{\n width: '32px', height: '32px',\n border: '3px solid #e5e7eb', borderTopColor: '#3b82f6',\n borderRadius: '50%',\n animation: 'spin 0.6s linear infinite',\n }} />\n <style>{`@keyframes spin { to { transform: rotate(360deg); } }`}</style>\n </div>\n );\n}\n\nexport function ProtectedRoute({\n children,\n requiredTier,\n fallback,\n loadingComponent,\n allowUnconfigured = false,\n loginPath = '/login',\n}: ProtectedRouteProps) {\n const { user, profile, loading, isConfigured } = useAuth();\n\n if (loading) {\n return <>{loadingComponent || <DefaultLoadingSpinner />}</>;\n }\n\n if (!isConfigured && allowUnconfigured) {\n return <>{children}</>;\n }\n\n if (!user) {\n if (fallback) return <>{fallback}</>;\n if (typeof window !== 'undefined') {\n window.location.href = loginPath;\n }\n return null;\n }\n\n if (requiredTier) {\n const userTier = profile?.subscription_tier || 'free';\n const userLevel = TIER_LEVELS[userTier] ?? 0;\n const requiredLevel = TIER_LEVELS[requiredTier] ?? 0;\n\n if (userLevel < requiredLevel) {\n return (\n <div style={{ textAlign: 'center', padding: '40px' }}>\n <h2 style={{ fontSize: '1.5rem', fontWeight: 600, marginBottom: '8px' }}>Upgrade Required</h2>\n <p style={{ color: '#6b7280' }}>\n This feature requires the {requiredTier} plan or higher.\n </p>\n </div>\n );\n }\n }\n\n return <>{children}</>;\n}\n","import { useState } from 'react';\nimport { useAuth } from './AuthProvider';\n\ninterface LoginFormProps {\n onSuccess?: () => void;\n onForgotPassword?: () => void;\n onSignupClick?: () => void;\n showOAuth?: boolean;\n className?: string;\n}\n\nexport function LoginForm({\n onSuccess,\n onForgotPassword,\n onSignupClick,\n showOAuth = true,\n className = '',\n}: LoginFormProps) {\n const { signIn, signInWithProvider, isConfigured } = useAuth();\n const [email, setEmail] = useState('');\n const [password, setPassword] = useState('');\n const [error, setError] = useState<string | null>(null);\n const [loading, setLoading] = useState(false);\n\n const handleSubmit = async (e: React.FormEvent) => {\n e.preventDefault();\n setError(null);\n setLoading(true);\n\n const result = await signIn(email, password);\n setLoading(false);\n\n if (result.error) {\n setError(result.error.message);\n } else {\n onSuccess?.();\n }\n };\n\n const handleOAuth = async (provider: string) => {\n setError(null);\n const result = await signInWithProvider(provider);\n if (result.error) {\n setError(result.error.message);\n }\n };\n\n if (!isConfigured) {\n return (\n <div style={{ padding: '20px', textAlign: 'center', color: '#6b7280' }}>\n Authentication is not configured. Connect a database to enable login.\n </div>\n );\n }\n\n return (\n <div className={className} style={{ maxWidth: '400px', margin: '0 auto' }}>\n <h2 style={{ fontSize: '1.5rem', fontWeight: 600, marginBottom: '24px', textAlign: 'center' }}>\n Sign In\n </h2>\n\n {error && (\n <div style={{ padding: '12px', marginBottom: '16px', backgroundColor: '#fef2f2', color: '#dc2626', borderRadius: '8px', fontSize: '14px' }}>\n {error}\n </div>\n )}\n\n <form onSubmit={handleSubmit}>\n <div style={{ marginBottom: '16px' }}>\n <label style={{ display: 'block', marginBottom: '4px', fontSize: '14px', fontWeight: 500 }}>Email</label>\n <input\n type=\"email\"\n value={email}\n onChange={(e) => setEmail(e.target.value)}\n required\n style={{ width: '100%', padding: '8px 12px', border: '1px solid #d1d5db', borderRadius: '6px', fontSize: '14px' }}\n />\n </div>\n\n <div style={{ marginBottom: '16px' }}>\n <label style={{ display: 'block', marginBottom: '4px', fontSize: '14px', fontWeight: 500 }}>Password</label>\n <input\n type=\"password\"\n value={password}\n onChange={(e) => setPassword(e.target.value)}\n required\n style={{ width: '100%', padding: '8px 12px', border: '1px solid #d1d5db', borderRadius: '6px', fontSize: '14px' }}\n />\n </div>\n\n {onForgotPassword && (\n <div style={{ marginBottom: '16px', textAlign: 'right' }}>\n <button type=\"button\" onClick={onForgotPassword} style={{ background: 'none', border: 'none', color: '#3b82f6', cursor: 'pointer', fontSize: '14px' }}>\n Forgot password?\n </button>\n </div>\n )}\n\n <button\n type=\"submit\"\n disabled={loading}\n style={{\n width: '100%', padding: '10px', backgroundColor: '#3b82f6', color: 'white',\n border: 'none', borderRadius: '6px', fontSize: '14px', fontWeight: 500,\n cursor: loading ? 'not-allowed' : 'pointer', opacity: loading ? 0.7 : 1,\n }}\n >\n {loading ? 'Signing in...' : 'Sign In'}\n </button>\n </form>\n\n {showOAuth && (\n <div style={{ marginTop: '24px' }}>\n <div style={{ textAlign: 'center', color: '#9ca3af', fontSize: '14px', marginBottom: '16px' }}>or continue with</div>\n <div style={{ display: 'flex', gap: '12px' }}>\n <button\n onClick={() => handleOAuth('google')}\n style={{ flex: 1, padding: '10px', border: '1px solid #d1d5db', borderRadius: '6px', background: 'white', cursor: 'pointer', fontSize: '14px' }}\n >\n Google\n </button>\n <button\n onClick={() => handleOAuth('github')}\n style={{ flex: 1, padding: '10px', border: '1px solid #d1d5db', borderRadius: '6px', background: 'white', cursor: 'pointer', fontSize: '14px' }}\n >\n GitHub\n </button>\n </div>\n </div>\n )}\n\n {onSignupClick && (\n <div style={{ marginTop: '24px', textAlign: 'center', fontSize: '14px' }}>\n Don&apos;t have an account?{' '}\n <button type=\"button\" onClick={onSignupClick} style={{ background: 'none', border: 'none', color: '#3b82f6', cursor: 'pointer', fontWeight: 500 }}>\n Sign up\n </button>\n </div>\n )}\n </div>\n );\n}\n","import { useState } from 'react';\nimport { useAuth } from './AuthProvider';\n\ninterface SignupFormProps {\n onSuccess?: () => void;\n onLoginClick?: () => void;\n showOAuth?: boolean;\n className?: string;\n}\n\nexport function SignupForm({\n onSuccess,\n onLoginClick,\n showOAuth = true,\n className = '',\n}: SignupFormProps) {\n const { signUp, signInWithProvider, isConfigured } = useAuth();\n const [name, setName] = useState('');\n const [email, setEmail] = useState('');\n const [password, setPassword] = useState('');\n const [agreed, setAgreed] = useState(false);\n const [error, setError] = useState<string | null>(null);\n const [success, setSuccess] = useState(false);\n const [loading, setLoading] = useState(false);\n\n const handleSubmit = async (e: React.FormEvent) => {\n e.preventDefault();\n if (!agreed) {\n setError('Please agree to the Terms of Service');\n return;\n }\n if (password.length < 8) {\n setError('Password must be at least 8 characters');\n return;\n }\n\n setError(null);\n setLoading(true);\n\n const result = await signUp(email, password, {\n metadata: { display_name: name },\n });\n setLoading(false);\n\n if (result.error) {\n setError(result.error.message);\n } else {\n setSuccess(true);\n onSuccess?.();\n }\n };\n\n const handleOAuth = async (provider: string) => {\n setError(null);\n const result = await signInWithProvider(provider);\n if (result.error) {\n setError(result.error.message);\n }\n };\n\n if (!isConfigured) {\n return (\n <div style={{ padding: '20px', textAlign: 'center', color: '#6b7280' }}>\n Authentication is not configured. Connect a database to enable signup.\n </div>\n );\n }\n\n if (success) {\n return (\n <div style={{ padding: '20px', textAlign: 'center' }}>\n <h3 style={{ fontSize: '1.25rem', fontWeight: 600, marginBottom: '8px', color: '#059669' }}>Check your email</h3>\n <p style={{ color: '#6b7280' }}>We sent a confirmation link to {email}</p>\n </div>\n );\n }\n\n return (\n <div className={className} style={{ maxWidth: '400px', margin: '0 auto' }}>\n <h2 style={{ fontSize: '1.5rem', fontWeight: 600, marginBottom: '24px', textAlign: 'center' }}>\n Create Account\n </h2>\n\n {error && (\n <div style={{ padding: '12px', marginBottom: '16px', backgroundColor: '#fef2f2', color: '#dc2626', borderRadius: '8px', fontSize: '14px' }}>\n {error}\n </div>\n )}\n\n <form onSubmit={handleSubmit}>\n <div style={{ marginBottom: '16px' }}>\n <label style={{ display: 'block', marginBottom: '4px', fontSize: '14px', fontWeight: 500 }}>Name</label>\n <input type=\"text\" value={name} onChange={(e) => setName(e.target.value)} required\n style={{ width: '100%', padding: '8px 12px', border: '1px solid #d1d5db', borderRadius: '6px', fontSize: '14px' }} />\n </div>\n\n <div style={{ marginBottom: '16px' }}>\n <label style={{ display: 'block', marginBottom: '4px', fontSize: '14px', fontWeight: 500 }}>Email</label>\n <input type=\"email\" value={email} onChange={(e) => setEmail(e.target.value)} required\n style={{ width: '100%', padding: '8px 12px', border: '1px solid #d1d5db', borderRadius: '6px', fontSize: '14px' }} />\n </div>\n\n <div style={{ marginBottom: '16px' }}>\n <label style={{ display: 'block', marginBottom: '4px', fontSize: '14px', fontWeight: 500 }}>Password</label>\n <input type=\"password\" value={password} onChange={(e) => setPassword(e.target.value)} required minLength={8}\n style={{ width: '100%', padding: '8px 12px', border: '1px solid #d1d5db', borderRadius: '6px', fontSize: '14px' }} />\n <span style={{ fontSize: '12px', color: '#9ca3af' }}>Minimum 8 characters</span>\n </div>\n\n <div style={{ marginBottom: '16px' }}>\n <label style={{ display: 'flex', alignItems: 'center', gap: '8px', fontSize: '14px', cursor: 'pointer' }}>\n <input type=\"checkbox\" checked={agreed} onChange={(e) => setAgreed(e.target.checked)} />\n I agree to the Terms of Service and Privacy Policy\n </label>\n </div>\n\n <button type=\"submit\" disabled={loading}\n style={{\n width: '100%', padding: '10px', backgroundColor: '#3b82f6', color: 'white',\n border: 'none', borderRadius: '6px', fontSize: '14px', fontWeight: 500,\n cursor: loading ? 'not-allowed' : 'pointer', opacity: loading ? 0.7 : 1,\n }}>\n {loading ? 'Creating account...' : 'Create Account'}\n </button>\n </form>\n\n {showOAuth && (\n <div style={{ marginTop: '24px' }}>\n <div style={{ textAlign: 'center', color: '#9ca3af', fontSize: '14px', marginBottom: '16px' }}>or continue with</div>\n <div style={{ display: 'flex', gap: '12px' }}>\n <button onClick={() => handleOAuth('google')}\n style={{ flex: 1, padding: '10px', border: '1px solid #d1d5db', borderRadius: '6px', background: 'white', cursor: 'pointer', fontSize: '14px' }}>\n Google\n </button>\n <button onClick={() => handleOAuth('github')}\n style={{ flex: 1, padding: '10px', border: '1px solid #d1d5db', borderRadius: '6px', background: 'white', cursor: 'pointer', fontSize: '14px' }}>\n GitHub\n </button>\n </div>\n </div>\n )}\n\n {onLoginClick && (\n <div style={{ marginTop: '24px', textAlign: 'center', fontSize: '14px' }}>\n Already have an account?{' '}\n <button type=\"button\" onClick={onLoginClick} style={{ background: 'none', border: 'none', color: '#3b82f6', cursor: 'pointer', fontWeight: 500 }}>\n Sign in\n </button>\n </div>\n )}\n </div>\n );\n}\n","import { useState } from 'react';\nimport { useAuth } from './AuthProvider';\n\ninterface ForgotPasswordFormProps {\n onBack?: () => void;\n className?: string;\n}\n\nexport function ForgotPasswordForm({ onBack, className = '' }: ForgotPasswordFormProps) {\n const { resetPassword } = useAuth();\n const [email, setEmail] = useState('');\n const [error, setError] = useState<string | null>(null);\n const [success, setSuccess] = useState(false);\n const [loading, setLoading] = useState(false);\n\n const handleSubmit = async (e: React.FormEvent) => {\n e.preventDefault();\n setError(null);\n setLoading(true);\n\n const result = await resetPassword(email);\n setLoading(false);\n\n if (result.error) {\n setError(result.error.message);\n } else {\n setSuccess(true);\n }\n };\n\n if (success) {\n return (\n <div className={className} style={{ maxWidth: '400px', margin: '0 auto', textAlign: 'center', padding: '20px' }}>\n <h3 style={{ fontSize: '1.25rem', fontWeight: 600, marginBottom: '8px', color: '#059669' }}>Check your email</h3>\n <p style={{ color: '#6b7280', marginBottom: '16px' }}>We sent a password reset link to {email}</p>\n {onBack && (\n <button type=\"button\" onClick={onBack} style={{ background: 'none', border: 'none', color: '#3b82f6', cursor: 'pointer', fontSize: '14px' }}>\n Back to login\n </button>\n )}\n </div>\n );\n }\n\n return (\n <div className={className} style={{ maxWidth: '400px', margin: '0 auto' }}>\n <h2 style={{ fontSize: '1.5rem', fontWeight: 600, marginBottom: '8px', textAlign: 'center' }}>Reset Password</h2>\n <p style={{ color: '#6b7280', textAlign: 'center', marginBottom: '24px', fontSize: '14px' }}>\n Enter your email and we&apos;ll send you a reset link\n </p>\n\n {error && (\n <div style={{ padding: '12px', marginBottom: '16px', backgroundColor: '#fef2f2', color: '#dc2626', borderRadius: '8px', fontSize: '14px' }}>\n {error}\n </div>\n )}\n\n <form onSubmit={handleSubmit}>\n <div style={{ marginBottom: '16px' }}>\n <label style={{ display: 'block', marginBottom: '4px', fontSize: '14px', fontWeight: 500 }}>Email</label>\n <input type=\"email\" value={email} onChange={(e) => setEmail(e.target.value)} required\n style={{ width: '100%', padding: '8px 12px', border: '1px solid #d1d5db', borderRadius: '6px', fontSize: '14px' }} />\n </div>\n\n <button type=\"submit\" disabled={loading}\n style={{\n width: '100%', padding: '10px', backgroundColor: '#3b82f6', color: 'white',\n border: 'none', borderRadius: '6px', fontSize: '14px', fontWeight: 500,\n cursor: loading ? 'not-allowed' : 'pointer', opacity: loading ? 0.7 : 1,\n }}>\n {loading ? 'Sending...' : 'Send Reset Link'}\n </button>\n </form>\n\n {onBack && (\n <div style={{ marginTop: '16px', textAlign: 'center' }}>\n <button type=\"button\" onClick={onBack} style={{ background: 'none', border: 'none', color: '#3b82f6', cursor: 'pointer', fontSize: '14px' }}>\n Back to login\n </button>\n </div>\n )}\n </div>\n );\n}\n","import { useEffect, useState } from 'react';\nimport { supabase } from '../core/supabase';\n\ninterface AuthCallbackProps {\n redirectTo?: string;\n loadingComponent?: React.ReactNode;\n}\n\nexport function AuthCallback({ redirectTo = '/', loadingComponent }: AuthCallbackProps) {\n const [error, setError] = useState<string | null>(null);\n\n useEffect(() => {\n const handleCallback = async () => {\n try {\n const { error } = await supabase.auth.getSession();\n if (error) {\n setError(error.message);\n return;\n }\n window.location.href = redirectTo;\n } catch (err: unknown) {\n setError(err instanceof Error ? err.message : 'Authentication callback failed');\n }\n };\n\n handleCallback();\n }, [redirectTo]);\n\n if (error) {\n return (\n <div style={{ textAlign: 'center', padding: '40px' }}>\n <h2 style={{ color: '#dc2626', marginBottom: '8px' }}>Authentication Error</h2>\n <p style={{ color: '#6b7280' }}>{error}</p>\n <a href=\"/login\" style={{ color: '#3b82f6', marginTop: '16px', display: 'inline-block' }}>\n Back to login\n </a>\n </div>\n );\n }\n\n return (\n <>\n {loadingComponent || (\n <div style={{ display: 'flex', alignItems: 'center', justifyContent: 'center', minHeight: '200px' }}>\n <p style={{ color: '#6b7280' }}>Completing authentication...</p>\n </div>\n )}\n </>\n );\n}\n"],"mappings":"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","names":["jsx","jsxs","useState","jsx","jsxs","useState","useState","jsx","jsxs","useState","useState","Fragment","jsx","jsxs","useState","error"]}
1
+ {"version":3,"sources":["../../src/auth/ProtectedRoute.tsx","../../src/auth/LoginForm.tsx","../../src/auth/SignupForm.tsx","../../src/auth/ForgotPasswordForm.tsx","../../src/auth/AuthCallback.tsx"],"sourcesContent":["import { useAuth } from './AuthProvider';\r\nimport type { SubscriptionTier } from '../core/types';\r\n\r\ninterface ProtectedRouteProps {\r\n children: React.ReactNode;\r\n requiredRoles?: string[];\r\n requiredTier?: SubscriptionTier;\r\n fallback?: React.ReactNode;\r\n unauthorizedFallback?: React.ReactNode;\r\n allowUnconfigured?: boolean;\r\n loadingComponent?: React.ReactNode;\r\n loginPath?: string;\r\n}\r\n\r\nconst TIER_LEVELS: Record<string, number> = {\r\n free: 0,\r\n starter: 1,\r\n creator: 2,\r\n pro: 3,\r\n business: 4,\r\n enterprise: 5,\r\n};\r\n\r\nfunction DefaultLoadingSpinner() {\r\n return (\r\n <div style={{ display: 'flex', alignItems: 'center', justifyContent: 'center', minHeight: '200px' }}>\r\n <div style={{\r\n width: '32px', height: '32px',\r\n border: '3px solid #e5e7eb', borderTopColor: '#3b82f6',\r\n borderRadius: '50%',\r\n animation: 'spin 0.6s linear infinite',\r\n }} />\r\n <style>{`@keyframes spin { to { transform: rotate(360deg); } }`}</style>\r\n </div>\r\n );\r\n}\r\n\r\nexport function ProtectedRoute({\r\n children,\r\n requiredTier,\r\n fallback,\r\n loadingComponent,\r\n allowUnconfigured = false,\r\n loginPath = '/login',\r\n}: ProtectedRouteProps) {\r\n const { user, profile, loading, isConfigured } = useAuth();\r\n\r\n if (loading) {\r\n return <>{loadingComponent || <DefaultLoadingSpinner />}</>;\r\n }\r\n\r\n if (!isConfigured && allowUnconfigured) {\r\n return <>{children}</>;\r\n }\r\n\r\n if (!user) {\r\n if (fallback) return <>{fallback}</>;\r\n if (typeof window !== 'undefined') {\r\n window.location.href = loginPath;\r\n }\r\n return null;\r\n }\r\n\r\n if (requiredTier) {\r\n const userTier = profile?.subscription_tier || 'free';\r\n const userLevel = TIER_LEVELS[userTier] ?? 0;\r\n const requiredLevel = TIER_LEVELS[requiredTier] ?? 0;\r\n\r\n if (userLevel < requiredLevel) {\r\n return (\r\n <div style={{ textAlign: 'center', padding: '40px' }}>\r\n <h2 style={{ fontSize: '1.5rem', fontWeight: 600, marginBottom: '8px' }}>Upgrade Required</h2>\r\n <p style={{ color: '#6b7280' }}>\r\n This feature requires the {requiredTier} plan or higher.\r\n </p>\r\n </div>\r\n );\r\n }\r\n }\r\n\r\n return <>{children}</>;\r\n}\r\n","import { useState } from 'react';\r\nimport { useAuth } from './AuthProvider';\r\n\r\ninterface LoginFormProps {\r\n onSuccess?: () => void;\r\n onForgotPassword?: () => void;\r\n onSignupClick?: () => void;\r\n showOAuth?: boolean;\r\n className?: string;\r\n}\r\n\r\nexport function LoginForm({\r\n onSuccess,\r\n onForgotPassword,\r\n onSignupClick,\r\n showOAuth = true,\r\n className = '',\r\n}: LoginFormProps) {\r\n const { signIn, signInWithProvider, isConfigured } = useAuth();\r\n const [email, setEmail] = useState('');\r\n const [password, setPassword] = useState('');\r\n const [error, setError] = useState<string | null>(null);\r\n const [loading, setLoading] = useState(false);\r\n\r\n const handleSubmit = async (e: React.FormEvent) => {\r\n e.preventDefault();\r\n setError(null);\r\n setLoading(true);\r\n\r\n const result = await signIn(email, password);\r\n setLoading(false);\r\n\r\n if (result.error) {\r\n setError(result.error.message);\r\n } else {\r\n onSuccess?.();\r\n }\r\n };\r\n\r\n const handleOAuth = async (provider: string) => {\r\n setError(null);\r\n const result = await signInWithProvider(provider);\r\n if (result.error) {\r\n setError(result.error.message);\r\n }\r\n };\r\n\r\n if (!isConfigured) {\r\n return (\r\n <div style={{ padding: '20px', textAlign: 'center', color: '#6b7280' }}>\r\n Authentication is not configured. Connect a database to enable login.\r\n </div>\r\n );\r\n }\r\n\r\n return (\r\n <div className={className} style={{ maxWidth: '400px', margin: '0 auto' }}>\r\n <h2 style={{ fontSize: '1.5rem', fontWeight: 600, marginBottom: '24px', textAlign: 'center' }}>\r\n Sign In\r\n </h2>\r\n\r\n {error && (\r\n <div style={{ padding: '12px', marginBottom: '16px', backgroundColor: '#fef2f2', color: '#dc2626', borderRadius: '8px', fontSize: '14px' }}>\r\n {error}\r\n </div>\r\n )}\r\n\r\n <form onSubmit={handleSubmit}>\r\n <div style={{ marginBottom: '16px' }}>\r\n <label style={{ display: 'block', marginBottom: '4px', fontSize: '14px', fontWeight: 500 }}>Email</label>\r\n <input\r\n type=\"email\"\r\n value={email}\r\n onChange={(e) => setEmail(e.target.value)}\r\n required\r\n style={{ width: '100%', padding: '8px 12px', border: '1px solid #d1d5db', borderRadius: '6px', fontSize: '14px' }}\r\n />\r\n </div>\r\n\r\n <div style={{ marginBottom: '16px' }}>\r\n <label style={{ display: 'block', marginBottom: '4px', fontSize: '14px', fontWeight: 500 }}>Password</label>\r\n <input\r\n type=\"password\"\r\n value={password}\r\n onChange={(e) => setPassword(e.target.value)}\r\n required\r\n style={{ width: '100%', padding: '8px 12px', border: '1px solid #d1d5db', borderRadius: '6px', fontSize: '14px' }}\r\n />\r\n </div>\r\n\r\n {onForgotPassword && (\r\n <div style={{ marginBottom: '16px', textAlign: 'right' }}>\r\n <button type=\"button\" onClick={onForgotPassword} style={{ background: 'none', border: 'none', color: '#3b82f6', cursor: 'pointer', fontSize: '14px' }}>\r\n Forgot password?\r\n </button>\r\n </div>\r\n )}\r\n\r\n <button\r\n type=\"submit\"\r\n disabled={loading}\r\n style={{\r\n width: '100%', padding: '10px', backgroundColor: '#3b82f6', color: 'white',\r\n border: 'none', borderRadius: '6px', fontSize: '14px', fontWeight: 500,\r\n cursor: loading ? 'not-allowed' : 'pointer', opacity: loading ? 0.7 : 1,\r\n }}\r\n >\r\n {loading ? 'Signing in...' : 'Sign In'}\r\n </button>\r\n </form>\r\n\r\n {showOAuth && (\r\n <div style={{ marginTop: '24px' }}>\r\n <div style={{ textAlign: 'center', color: '#9ca3af', fontSize: '14px', marginBottom: '16px' }}>or continue with</div>\r\n <div style={{ display: 'flex', gap: '12px' }}>\r\n <button\r\n onClick={() => handleOAuth('google')}\r\n style={{ flex: 1, padding: '10px', border: '1px solid #d1d5db', borderRadius: '6px', background: 'white', cursor: 'pointer', fontSize: '14px' }}\r\n >\r\n Google\r\n </button>\r\n <button\r\n onClick={() => handleOAuth('github')}\r\n style={{ flex: 1, padding: '10px', border: '1px solid #d1d5db', borderRadius: '6px', background: 'white', cursor: 'pointer', fontSize: '14px' }}\r\n >\r\n GitHub\r\n </button>\r\n </div>\r\n </div>\r\n )}\r\n\r\n {onSignupClick && (\r\n <div style={{ marginTop: '24px', textAlign: 'center', fontSize: '14px' }}>\r\n Don&apos;t have an account?{' '}\r\n <button type=\"button\" onClick={onSignupClick} style={{ background: 'none', border: 'none', color: '#3b82f6', cursor: 'pointer', fontWeight: 500 }}>\r\n Sign up\r\n </button>\r\n </div>\r\n )}\r\n </div>\r\n );\r\n}\r\n","import { useState } from 'react';\r\nimport { useAuth } from './AuthProvider';\r\n\r\ninterface SignupFormProps {\r\n onSuccess?: () => void;\r\n onLoginClick?: () => void;\r\n showOAuth?: boolean;\r\n className?: string;\r\n}\r\n\r\nexport function SignupForm({\r\n onSuccess,\r\n onLoginClick,\r\n showOAuth = true,\r\n className = '',\r\n}: SignupFormProps) {\r\n const { signUp, signInWithProvider, isConfigured } = useAuth();\r\n const [name, setName] = useState('');\r\n const [email, setEmail] = useState('');\r\n const [password, setPassword] = useState('');\r\n const [agreed, setAgreed] = useState(false);\r\n const [error, setError] = useState<string | null>(null);\r\n const [success, setSuccess] = useState(false);\r\n const [loading, setLoading] = useState(false);\r\n\r\n const handleSubmit = async (e: React.FormEvent) => {\r\n e.preventDefault();\r\n if (!agreed) {\r\n setError('Please agree to the Terms of Service');\r\n return;\r\n }\r\n if (password.length < 8) {\r\n setError('Password must be at least 8 characters');\r\n return;\r\n }\r\n\r\n setError(null);\r\n setLoading(true);\r\n\r\n const result = await signUp(email, password, {\r\n metadata: { display_name: name },\r\n });\r\n setLoading(false);\r\n\r\n if (result.error) {\r\n setError(result.error.message);\r\n } else {\r\n setSuccess(true);\r\n onSuccess?.();\r\n }\r\n };\r\n\r\n const handleOAuth = async (provider: string) => {\r\n setError(null);\r\n const result = await signInWithProvider(provider);\r\n if (result.error) {\r\n setError(result.error.message);\r\n }\r\n };\r\n\r\n if (!isConfigured) {\r\n return (\r\n <div style={{ padding: '20px', textAlign: 'center', color: '#6b7280' }}>\r\n Authentication is not configured. Connect a database to enable signup.\r\n </div>\r\n );\r\n }\r\n\r\n if (success) {\r\n return (\r\n <div style={{ padding: '20px', textAlign: 'center' }}>\r\n <h3 style={{ fontSize: '1.25rem', fontWeight: 600, marginBottom: '8px', color: '#059669' }}>Check your email</h3>\r\n <p style={{ color: '#6b7280' }}>We sent a confirmation link to {email}</p>\r\n </div>\r\n );\r\n }\r\n\r\n return (\r\n <div className={className} style={{ maxWidth: '400px', margin: '0 auto' }}>\r\n <h2 style={{ fontSize: '1.5rem', fontWeight: 600, marginBottom: '24px', textAlign: 'center' }}>\r\n Create Account\r\n </h2>\r\n\r\n {error && (\r\n <div style={{ padding: '12px', marginBottom: '16px', backgroundColor: '#fef2f2', color: '#dc2626', borderRadius: '8px', fontSize: '14px' }}>\r\n {error}\r\n </div>\r\n )}\r\n\r\n <form onSubmit={handleSubmit}>\r\n <div style={{ marginBottom: '16px' }}>\r\n <label style={{ display: 'block', marginBottom: '4px', fontSize: '14px', fontWeight: 500 }}>Name</label>\r\n <input type=\"text\" value={name} onChange={(e) => setName(e.target.value)} required\r\n style={{ width: '100%', padding: '8px 12px', border: '1px solid #d1d5db', borderRadius: '6px', fontSize: '14px' }} />\r\n </div>\r\n\r\n <div style={{ marginBottom: '16px' }}>\r\n <label style={{ display: 'block', marginBottom: '4px', fontSize: '14px', fontWeight: 500 }}>Email</label>\r\n <input type=\"email\" value={email} onChange={(e) => setEmail(e.target.value)} required\r\n style={{ width: '100%', padding: '8px 12px', border: '1px solid #d1d5db', borderRadius: '6px', fontSize: '14px' }} />\r\n </div>\r\n\r\n <div style={{ marginBottom: '16px' }}>\r\n <label style={{ display: 'block', marginBottom: '4px', fontSize: '14px', fontWeight: 500 }}>Password</label>\r\n <input type=\"password\" value={password} onChange={(e) => setPassword(e.target.value)} required minLength={8}\r\n style={{ width: '100%', padding: '8px 12px', border: '1px solid #d1d5db', borderRadius: '6px', fontSize: '14px' }} />\r\n <span style={{ fontSize: '12px', color: '#9ca3af' }}>Minimum 8 characters</span>\r\n </div>\r\n\r\n <div style={{ marginBottom: '16px' }}>\r\n <label style={{ display: 'flex', alignItems: 'center', gap: '8px', fontSize: '14px', cursor: 'pointer' }}>\r\n <input type=\"checkbox\" checked={agreed} onChange={(e) => setAgreed(e.target.checked)} />\r\n I agree to the Terms of Service and Privacy Policy\r\n </label>\r\n </div>\r\n\r\n <button type=\"submit\" disabled={loading}\r\n style={{\r\n width: '100%', padding: '10px', backgroundColor: '#3b82f6', color: 'white',\r\n border: 'none', borderRadius: '6px', fontSize: '14px', fontWeight: 500,\r\n cursor: loading ? 'not-allowed' : 'pointer', opacity: loading ? 0.7 : 1,\r\n }}>\r\n {loading ? 'Creating account...' : 'Create Account'}\r\n </button>\r\n </form>\r\n\r\n {showOAuth && (\r\n <div style={{ marginTop: '24px' }}>\r\n <div style={{ textAlign: 'center', color: '#9ca3af', fontSize: '14px', marginBottom: '16px' }}>or continue with</div>\r\n <div style={{ display: 'flex', gap: '12px' }}>\r\n <button onClick={() => handleOAuth('google')}\r\n style={{ flex: 1, padding: '10px', border: '1px solid #d1d5db', borderRadius: '6px', background: 'white', cursor: 'pointer', fontSize: '14px' }}>\r\n Google\r\n </button>\r\n <button onClick={() => handleOAuth('github')}\r\n style={{ flex: 1, padding: '10px', border: '1px solid #d1d5db', borderRadius: '6px', background: 'white', cursor: 'pointer', fontSize: '14px' }}>\r\n GitHub\r\n </button>\r\n </div>\r\n </div>\r\n )}\r\n\r\n {onLoginClick && (\r\n <div style={{ marginTop: '24px', textAlign: 'center', fontSize: '14px' }}>\r\n Already have an account?{' '}\r\n <button type=\"button\" onClick={onLoginClick} style={{ background: 'none', border: 'none', color: '#3b82f6', cursor: 'pointer', fontWeight: 500 }}>\r\n Sign in\r\n </button>\r\n </div>\r\n )}\r\n </div>\r\n );\r\n}\r\n","import { useState } from 'react';\r\nimport { useAuth } from './AuthProvider';\r\n\r\ninterface ForgotPasswordFormProps {\r\n onBack?: () => void;\r\n className?: string;\r\n}\r\n\r\nexport function ForgotPasswordForm({ onBack, className = '' }: ForgotPasswordFormProps) {\r\n const { resetPassword } = useAuth();\r\n const [email, setEmail] = useState('');\r\n const [error, setError] = useState<string | null>(null);\r\n const [success, setSuccess] = useState(false);\r\n const [loading, setLoading] = useState(false);\r\n\r\n const handleSubmit = async (e: React.FormEvent) => {\r\n e.preventDefault();\r\n setError(null);\r\n setLoading(true);\r\n\r\n const result = await resetPassword(email);\r\n setLoading(false);\r\n\r\n if (result.error) {\r\n setError(result.error.message);\r\n } else {\r\n setSuccess(true);\r\n }\r\n };\r\n\r\n if (success) {\r\n return (\r\n <div className={className} style={{ maxWidth: '400px', margin: '0 auto', textAlign: 'center', padding: '20px' }}>\r\n <h3 style={{ fontSize: '1.25rem', fontWeight: 600, marginBottom: '8px', color: '#059669' }}>Check your email</h3>\r\n <p style={{ color: '#6b7280', marginBottom: '16px' }}>We sent a password reset link to {email}</p>\r\n {onBack && (\r\n <button type=\"button\" onClick={onBack} style={{ background: 'none', border: 'none', color: '#3b82f6', cursor: 'pointer', fontSize: '14px' }}>\r\n Back to login\r\n </button>\r\n )}\r\n </div>\r\n );\r\n }\r\n\r\n return (\r\n <div className={className} style={{ maxWidth: '400px', margin: '0 auto' }}>\r\n <h2 style={{ fontSize: '1.5rem', fontWeight: 600, marginBottom: '8px', textAlign: 'center' }}>Reset Password</h2>\r\n <p style={{ color: '#6b7280', textAlign: 'center', marginBottom: '24px', fontSize: '14px' }}>\r\n Enter your email and we&apos;ll send you a reset link\r\n </p>\r\n\r\n {error && (\r\n <div style={{ padding: '12px', marginBottom: '16px', backgroundColor: '#fef2f2', color: '#dc2626', borderRadius: '8px', fontSize: '14px' }}>\r\n {error}\r\n </div>\r\n )}\r\n\r\n <form onSubmit={handleSubmit}>\r\n <div style={{ marginBottom: '16px' }}>\r\n <label style={{ display: 'block', marginBottom: '4px', fontSize: '14px', fontWeight: 500 }}>Email</label>\r\n <input type=\"email\" value={email} onChange={(e) => setEmail(e.target.value)} required\r\n style={{ width: '100%', padding: '8px 12px', border: '1px solid #d1d5db', borderRadius: '6px', fontSize: '14px' }} />\r\n </div>\r\n\r\n <button type=\"submit\" disabled={loading}\r\n style={{\r\n width: '100%', padding: '10px', backgroundColor: '#3b82f6', color: 'white',\r\n border: 'none', borderRadius: '6px', fontSize: '14px', fontWeight: 500,\r\n cursor: loading ? 'not-allowed' : 'pointer', opacity: loading ? 0.7 : 1,\r\n }}>\r\n {loading ? 'Sending...' : 'Send Reset Link'}\r\n </button>\r\n </form>\r\n\r\n {onBack && (\r\n <div style={{ marginTop: '16px', textAlign: 'center' }}>\r\n <button type=\"button\" onClick={onBack} style={{ background: 'none', border: 'none', color: '#3b82f6', cursor: 'pointer', fontSize: '14px' }}>\r\n Back to login\r\n </button>\r\n </div>\r\n )}\r\n </div>\r\n );\r\n}\r\n","import { useEffect, useState } from 'react';\r\nimport { supabase } from '../core/supabase';\r\n\r\ninterface AuthCallbackProps {\r\n redirectTo?: string;\r\n loadingComponent?: React.ReactNode;\r\n}\r\n\r\nexport function AuthCallback({ redirectTo = '/', loadingComponent }: AuthCallbackProps) {\r\n const [error, setError] = useState<string | null>(null);\r\n\r\n useEffect(() => {\r\n const handleCallback = async () => {\r\n try {\r\n // With detectSessionInUrl + PKCE the client usually auto-exchanges the\r\n // `?code=` before we run, so getSession() already has it. If not (e.g. a\r\n // build with detectSessionInUrl disabled), exchange explicitly.\r\n let session = null;\r\n const got = await supabase.auth.getSession();\r\n if (got.error) { setError(got.error.message); return; }\r\n session = got.data?.session ?? null;\r\n\r\n if (!session && typeof window !== 'undefined' &&\r\n new URLSearchParams(window.location.search).get('code')) {\r\n const ex = await supabase.auth.exchangeCodeForSession(window.location.href);\r\n if (ex.error) { setError(ex.error.message); return; }\r\n session = ex.data?.session ?? null;\r\n }\r\n\r\n // Popup flow (in-editor / framed sign-in): notify the opener and close,\r\n // rather than navigating. The opener (AuthProvider) picks up the session.\r\n if (typeof window !== 'undefined' && window.opener && window.opener !== window) {\r\n try { window.opener.postMessage({ type: 'ezc-auth-complete' }, '*'); } catch { /* cross-origin opener */ }\r\n window.close();\r\n return;\r\n }\r\n\r\n window.location.href = redirectTo;\r\n } catch (err: unknown) {\r\n setError(err instanceof Error ? err.message : 'Authentication callback failed');\r\n }\r\n };\r\n\r\n handleCallback();\r\n }, [redirectTo]);\r\n\r\n if (error) {\r\n return (\r\n <div style={{ textAlign: 'center', padding: '40px' }}>\r\n <h2 style={{ color: '#dc2626', marginBottom: '8px' }}>Authentication Error</h2>\r\n <p style={{ color: '#6b7280' }}>{error}</p>\r\n <a href=\"/login\" style={{ color: '#3b82f6', marginTop: '16px', display: 'inline-block' }}>\r\n Back to login\r\n </a>\r\n </div>\r\n );\r\n }\r\n\r\n return (\r\n <>\r\n {loadingComponent || (\r\n <div style={{ display: 'flex', alignItems: 'center', justifyContent: 'center', minHeight: '200px' }}>\r\n <p style={{ color: '#6b7280' }}>Completing authentication...</p>\r\n </div>\r\n )}\r\n </>\r\n );\r\n}\r\n"],"mappings":"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","names":["jsx","jsxs","useState","jsx","jsxs","useState","useState","jsx","jsxs","useState","useState","Fragment","jsx","jsxs","useState"]}
@@ -0,0 +1,44 @@
1
+ import {
2
+ env
3
+ } from "./chunk-LIUE7M7K.js";
4
+
5
+ // src/core/projectToken.ts
6
+ function isBrowserRuntime() {
7
+ return typeof window !== "undefined" && typeof window.document !== "undefined";
8
+ }
9
+ function resolveServerToken() {
10
+ const serverToken = env.EZC_PROJECT_TOKEN_SERVER;
11
+ if (typeof serverToken === "string" && serverToken.length > 0) {
12
+ return { ok: true, token: serverToken, source: "server-class" };
13
+ }
14
+ const legacyToken = env.EZC_PROJECT_TOKEN_LEGACY;
15
+ if (typeof legacyToken === "string" && legacyToken.length > 0) {
16
+ warnLegacyOnce();
17
+ return { ok: true, token: legacyToken, source: "legacy" };
18
+ }
19
+ if (isBrowserRuntime()) {
20
+ return {
21
+ ok: false,
22
+ reason: "This SDK function must be called from server-side code; EZC_PROJECT_TOKEN_SERVER is not available in browser bundles. Move the call to a Next.js API route, server action, or Node script."
23
+ };
24
+ }
25
+ return {
26
+ ok: false,
27
+ reason: "EZC_PROJECT_TOKEN_SERVER is not configured. Set it in your server environment (e.g. via fly.io secrets, .env.local, or your deploy provider)."
28
+ };
29
+ }
30
+ var legacyWarnIssued = false;
31
+ function warnLegacyOnce() {
32
+ if (legacyWarnIssued) return;
33
+ legacyWarnIssued = true;
34
+ if (typeof console !== "undefined" && typeof console.warn === "function") {
35
+ console.warn(
36
+ "[ezcoder-sdk] EZC_PROJECT_TOKEN is deprecated. Migrate to the two-class pair (EZC_PROJECT_TOKEN_PUBLIC + EZC_PROJECT_TOKEN_SERVER); the legacy single-token will be removed in Phase 2 of the B1 rollout."
37
+ );
38
+ }
39
+ }
40
+
41
+ export {
42
+ resolveServerToken
43
+ };
44
+ //# sourceMappingURL=chunk-CQKYANAW.js.map