@solidxai/core-ui 0.1.7-beta.10 → 0.1.7-beta.11

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 (88) hide show
  1. package/README.md +215 -0
  2. package/dist/components/auth/SolidOTPVerify.d.ts +3 -0
  3. package/dist/components/auth/SolidOTPVerify.d.ts.map +1 -0
  4. package/dist/components/auth/SolidOTPVerify.js +67 -0
  5. package/dist/components/auth/SolidOTPVerify.js.map +1 -0
  6. package/dist/components/auth/SolidOTPVerify.tsx +133 -0
  7. package/dist/components/common/AuthBanner.js.map +1 -1
  8. package/dist/components/common/GeneralSettings.js +31 -29
  9. package/dist/components/common/GeneralSettings.js.map +1 -1
  10. package/dist/components/common/GeneralSettings.tsx +51 -41
  11. package/dist/components/common/SolidSettings/LlmSettings/AiModelConfigTab.d.ts +18 -14
  12. package/dist/components/common/SolidSettings/LlmSettings/AiModelConfigTab.d.ts.map +1 -1
  13. package/dist/components/common/SolidSettings/LlmSettings/AiModelConfigTab.js +130 -26
  14. package/dist/components/common/SolidSettings/LlmSettings/AiModelConfigTab.js.map +1 -1
  15. package/dist/components/common/SolidSettings/LlmSettings/AiModelConfigTab.tsx +319 -80
  16. package/dist/components/core/common/LoadDynamicJsxComponent.d.ts +2 -0
  17. package/dist/components/core/common/LoadDynamicJsxComponent.d.ts.map +1 -0
  18. package/dist/components/core/common/LoadDynamicJsxComponent.js +50 -0
  19. package/dist/components/core/common/LoadDynamicJsxComponent.js.map +1 -0
  20. package/dist/components/core/common/LoadDynamicJsxComponent.tsx +70 -0
  21. package/dist/components/core/kanban/SolidManyToOneFilterElement.d.ts.map +1 -1
  22. package/dist/components/core/kanban/SolidManyToOneFilterElement.js.map +1 -1
  23. package/dist/components/core/kanban/SolidManyToOneFilterElement.tsx +2 -1
  24. package/dist/components/core/kanban/kanban-fields/SolidMediaMultipleKanbanField.d.ts.map +1 -1
  25. package/dist/components/core/kanban/kanban-fields/SolidMediaMultipleKanbanField.js +2 -2
  26. package/dist/components/core/kanban/kanban-fields/SolidMediaMultipleKanbanField.js.map +1 -1
  27. package/dist/components/core/kanban/kanban-fields/SolidMediaMultipleKanbanField.tsx +10 -21
  28. package/dist/components/core/kanban/kanban-fields/SolidMediaSingleKanbanField.d.ts.map +1 -1
  29. package/dist/components/core/kanban/kanban-fields/SolidMediaSingleKanbanField.js +2 -2
  30. package/dist/components/core/kanban/kanban-fields/SolidMediaSingleKanbanField.js.map +1 -1
  31. package/dist/components/core/kanban/kanban-fields/SolidMediaSingleKanbanField.tsx +10 -18
  32. package/dist/components/core/kanban/kanban-fields/SolidShortTextKanbanField.d.ts.map +1 -1
  33. package/dist/components/core/kanban/kanban-fields/SolidShortTextKanbanField.js +6 -3
  34. package/dist/components/core/kanban/kanban-fields/SolidShortTextKanbanField.js.map +1 -1
  35. package/dist/components/core/kanban/kanban-fields/SolidShortTextKanbanField.tsx +24 -30
  36. package/dist/components/core/kanban/kanban-fields/relations/SolidRelationManyToOneKanbanField.js.map +1 -1
  37. package/dist/components/core/kanban/kanban-fields/relations/SolidRelationManyToOneKanbanField.tsx +2 -2
  38. package/dist/components/core/list/SolidListViewRowButtonContextMenu.d.ts +1 -1
  39. package/dist/components/core/list/SolidListViewRowButtonContextMenu.d.ts.map +1 -1
  40. package/dist/components/core/list/SolidListViewRowButtonContextMenu.js +7 -6
  41. package/dist/components/core/list/SolidListViewRowButtonContextMenu.js.map +1 -1
  42. package/dist/components/core/list/SolidListViewRowButtonContextMenu.tsx +10 -9
  43. package/dist/components/shad-cn-ui/SolidTabs.d.ts +2 -1
  44. package/dist/components/shad-cn-ui/SolidTabs.d.ts.map +1 -1
  45. package/dist/components/shad-cn-ui/SolidTabs.js +5 -5
  46. package/dist/components/shad-cn-ui/SolidTabs.js.map +1 -1
  47. package/dist/components/shad-cn-ui/SolidTabs.tsx +6 -0
  48. package/dist/nextAuth/authProviders.d.ts +4 -0
  49. package/dist/nextAuth/authProviders.d.ts.map +1 -0
  50. package/dist/nextAuth/authProviders.js +198 -0
  51. package/dist/nextAuth/authProviders.js.map +1 -0
  52. package/dist/nextAuth/authProviders.tsx +232 -0
  53. package/dist/nextAuth/handleLogout.d.ts +2 -0
  54. package/dist/nextAuth/handleLogout.d.ts.map +1 -0
  55. package/dist/nextAuth/handleLogout.js +36 -0
  56. package/dist/nextAuth/handleLogout.js.map +1 -0
  57. package/dist/nextAuth/handleLogout.tsx +39 -0
  58. package/dist/nextAuth/refreshAccessToken.d.ts +2 -0
  59. package/dist/nextAuth/refreshAccessToken.d.ts.map +1 -0
  60. package/dist/nextAuth/refreshAccessToken.js +24 -0
  61. package/dist/nextAuth/refreshAccessToken.js.map +1 -0
  62. package/dist/nextAuth/refreshAccessToken.tsx +28 -0
  63. package/dist/redux/features/settingsSlice.d.ts +20 -0
  64. package/dist/redux/features/settingsSlice.d.ts.map +1 -0
  65. package/dist/redux/features/settingsSlice.js +39 -0
  66. package/dist/redux/features/settingsSlice.js.map +1 -0
  67. package/dist/redux/features/settingsSlice.ts +60 -0
  68. package/package.json +1 -1
  69. package/dist/components/core/list/SolidDataTablePagination.d.ts +0 -15
  70. package/dist/components/core/list/SolidDataTablePagination.d.ts.map +0 -1
  71. package/dist/components/core/list/SolidDataTablePagination.js +0 -22
  72. package/dist/components/core/list/SolidDataTablePagination.js.map +0 -1
  73. package/dist/components/core/list/SolidDataTablePagination.tsx +0 -71
  74. package/dist/components/solid-ui/SolidButton.d.ts +0 -14
  75. package/dist/components/solid-ui/SolidButton.d.ts.map +0 -1
  76. package/dist/components/solid-ui/SolidButton.js +0 -36
  77. package/dist/components/solid-ui/SolidButton.js.map +0 -1
  78. package/dist/components/solid-ui/SolidButton.tsx +0 -54
  79. package/dist/components/solid-ui/SolidTabs.d.ts +0 -18
  80. package/dist/components/solid-ui/SolidTabs.d.ts.map +0 -1
  81. package/dist/components/solid-ui/SolidTabs.js +0 -22
  82. package/dist/components/solid-ui/SolidTabs.js.map +0 -1
  83. package/dist/components/solid-ui/SolidTabs.tsx +0 -73
  84. package/dist/components/solid-ui/index.d.ts +0 -3
  85. package/dist/components/solid-ui/index.d.ts.map +0 -1
  86. package/dist/components/solid-ui/index.js +0 -3
  87. package/dist/components/solid-ui/index.js.map +0 -1
  88. package/dist/components/solid-ui/index.ts +0 -2
package/README.md ADDED
@@ -0,0 +1,215 @@
1
+ # @solidxai/core-ui
2
+
3
+ > The React UI framework behind every SolidX application — auth flows, metadata-driven forms and tables, dashboards, and full state management — wired up and ready to use.
4
+
5
+ `@solidxai/core-ui` is the frontend counterpart to [`@solidxai/core`](https://www.npmjs.com/package/@solidxai/core). It ships a complete set of React components, Redux slices, RTK Query API integrations, route guards, and utility hooks designed to work with the SolidX backend platform — so you can build production-grade admin and data-management interfaces without rebuilding the same infrastructure on every project.
6
+
7
+ [![npm version](https://img.shields.io/npm/v/@solidxai/core-ui)](https://www.npmjs.com/package/@solidxai/core-ui)
8
+ [![License: BSL](https://img.shields.io/badge/License-BSL-blue.svg)](https://opensource.org/licenses/BSL-1.1)
9
+ [![Documentation](https://img.shields.io/badge/docs-solidxai.com-blue)](https://docs.solidxai.com/docs)
10
+
11
+
12
+ ## Why @solidxai/core-ui?
13
+
14
+ Building admin dashboards and data-management UIs involves the same heavy lifting every time: authentication screens, data tables with filtering and pagination, form builders for every field type, role-aware UI elements, file upload flows, and a global state layer that ties it all together.
15
+
16
+ `@solidxai/core-ui` bundles all of that into a single, cohesive package that is:
17
+
18
+ - **Metadata-driven** — point `SolidListView` or `SolidFormView` at a model name and get a fully functional table or form without writing column definitions or field components by hand.
19
+ - **Fully typed** — complete TypeScript definitions for every component, hook, slice, and utility.
20
+ - **Extensible** — register custom components and functions into the extension registry; the core engine picks them up automatically.
21
+ - **Backend-agnostic escape hatches** — pre-configured Axios instance and RTK Query base query, but nothing prevents you from calling your own endpoints alongside them.
22
+
23
+
24
+ ## Core Capabilities
25
+
26
+ ### Metadata-driven Views
27
+
28
+ The centrepiece of the library. Describe your data model once and get complete UI for free.
29
+
30
+ - **`SolidListView`** — data table with multi-column sorting, rich filter expressions, group-by, column visibility, row actions, import/export, and pagination; supports 15+ column types including relations, media, rich text, and computed fields.
31
+ - **`SolidFormView`** — full create/edit form rendered from model metadata; supports 15+ field types — boolean, date/time, decimal, integer, short/long text, rich text, JSON, media (single & multiple), static/dynamic selection, relation, email, password, and more.
32
+ - **`SolidFormStepper`** — multi-step wizard wrapper for any form.
33
+ - **`SolidTreeView` / `SolidTreeTable`** — hierarchical tree display, with optional table columns.
34
+ - **`SolidKanbanView`** — kanban board view backed by the same model metadata.
35
+
36
+ ### Authentication
37
+
38
+ Complete auth UI with no extra wiring needed.
39
+
40
+ - Login, registration, forgot/reset password, and force-change-password screens
41
+ - OTP / passwordless flows (SMS and email)
42
+ - Google OAuth2 integration
43
+ - JWT access/refresh token management via `authSlice` and the `baseQueryWithAuth` RTK Query adapter
44
+ - `AuthGuard` and `GuestGuard` route protection components
45
+
46
+ ### Layouts & Navigation
47
+
48
+ - `AdminLayout` / `Layout` — shell layouts with sidebar, header, and footer regions
49
+ - `SolidAiStudioLayout` / `SolidStudio` — studio/configuration mode for admin users
50
+ - `NavbarOne`, `NavbarTwo` — responsive top navigation bars
51
+ - `AdminSidebar`, `UserSidebar` — collapsible sidebars
52
+ - `GlobalSearch` — application-wide search component
53
+ - `FilterMenu` — slide-in advanced filter panel
54
+
55
+ ### Dashboards
56
+
57
+ - `SolidDashboard` — drag-and-drop dashboard grid backed by Gridstack
58
+ - `SolidViewLayoutManager` — layout composer for arranging views
59
+ - Chart.js integration: bar, line, pie, doughnut, data table, and meter-group chart types
60
+ - Security-aware aggregates that respect the active user's role
61
+
62
+ ### Redux Store & API Layer
63
+
64
+ A pre-wired Redux Toolkit store with slices and RTK Query API definitions ready to drop in.
65
+
66
+ | Slices | Purpose |
67
+ |---|---|
68
+ | `authSlice` | Token storage and logout |
69
+ | `userSlice` | Current user and authentication state |
70
+ | `themeSlice` | Light / dark theme |
71
+ | `toastSlice` | Toast notification queue |
72
+ | `popupSlice` | Modal open/close state |
73
+ | `navbarSlice` | Navbar visibility |
74
+ | `dataViewSlice` | Grid vs list view toggle |
75
+
76
+ API slices (RTK Query) cover: auth, users, roles, modules, models, fields, views, menus, media, import/export, dashboards, settings, chatter, API keys, and AI interactions.
77
+
78
+ ### UI Component Library
79
+
80
+ A complete set of primitives built on Radix UI, PrimeReact, and Bootstrap, including:
81
+
82
+ - Buttons, inputs, textareas, password fields, date pickers, autocomplete
83
+ - Dialogs, popovers, tooltips, accordions, tabs, dropdowns
84
+ - Checkboxes, radio groups, switches, sliders, progress bars
85
+ - Rich text editor (Quill), code editor (Monaco / CodeMirror)
86
+ - Media lightbox, image viewer, PDF viewer
87
+ - `SolidIcon` — custom icon registry backed by Lucide React
88
+
89
+ ### State, Routing & Providers
90
+
91
+ - `StoreProvider` — wraps the app with the Redux store
92
+ - `SolidThemeProvider` — theme context
93
+ - `SolidToastProvider` — toast notification context
94
+ - `SolidLayoutRegistryProvider` — layout registry context
95
+ - `getSolidRoutes` — generates the full route tree from module metadata
96
+ - `useSession`, `useRouter`, `usePathname`, `useSearchParams` — familiar routing hooks
97
+
98
+ ### Utilities & Helpers
99
+
100
+ - `solidAxios` — pre-configured Axios instance with auth headers
101
+ - `solidGet`, `solidPost`, `solidPut`, `solidPatch`, `solidDelete` — typed HTTP helpers
102
+ - `signIn`, `signOut`, `getSession`, `refreshAccessToken` — auth session helpers
103
+ - `permissionExpression`, `hasAnyRole` — permission evaluation helpers
104
+ - `downloadFileWithProgress`, `downloadMediaFile`, `fetchS3Url` — file utilities
105
+ - `eventBus` / `AppEvents` — application-wide event system
106
+ - `registerExtensionComponent`, `registerExtensionFunction` — extension registry
107
+
108
+ ### Chatter
109
+
110
+ - `SolidChatter` — per-record messaging thread and activity feed component, mirroring the backend Chatter feature
111
+
112
+
113
+ ## Installation
114
+
115
+ ```bash
116
+ npm install @solidxai/core-ui
117
+ ```
118
+
119
+ ### Peer dependencies
120
+
121
+ ```bash
122
+ npm install react react-dom react-router-dom \
123
+ @reduxjs/toolkit react-redux \
124
+ bootstrap primereact primeicons primeflex
125
+ ```
126
+
127
+
128
+ ## Quick Setup
129
+
130
+ ### 1. Create the store
131
+
132
+ ```typescript
133
+ import { createSolidStore } from '@solidxai/core-ui';
134
+
135
+ export const store = createSolidStore({
136
+ entities: ['User', 'Post'], // your entity names
137
+ reducers: { mySlice: myReducer },
138
+ middlewares: [myMiddleware],
139
+ });
140
+ ```
141
+
142
+ ### 2. Wrap your app
143
+
144
+ ```typescript
145
+ import {
146
+ StoreProvider,
147
+ SolidThemeProvider,
148
+ SolidToastProvider,
149
+ } from '@solidxai/core-ui';
150
+
151
+ export default function App() {
152
+ return (
153
+ <StoreProvider store={store}>
154
+ <SolidThemeProvider>
155
+ <SolidToastProvider>
156
+ <Router />
157
+ </SolidToastProvider>
158
+ </SolidThemeProvider>
159
+ </StoreProvider>
160
+ );
161
+ }
162
+ ```
163
+
164
+ ### 3. Use metadata-driven views
165
+
166
+ ```typescript
167
+ import { SolidListView, SolidFormView } from '@solidxai/core-ui';
168
+
169
+ // Renders a full data table for the "users" model
170
+ <SolidListView moduleName="users" viewName="list" />
171
+
172
+ // Renders a create/edit form for the "users" model
173
+ <SolidFormView moduleName="users" viewName="create" />
174
+ ```
175
+
176
+ For full configuration options — environment variables, theming, extension points, and advanced layout setup — see the [Developer Documentation](https://docs.solidxai.com/docs).
177
+
178
+
179
+ ## Technology Stack
180
+
181
+ | Concern | Technology |
182
+ |---|---|
183
+ | Framework | React 18 + TypeScript |
184
+ | Routing | React Router DOM 7 |
185
+ | State management | Redux Toolkit + RTK Query |
186
+ | HTTP | Axios |
187
+ | UI primitives | Radix UI · PrimeReact · Bootstrap 5 |
188
+ | Data tables | TanStack Table 8 |
189
+ | Charts | Chart.js |
190
+ | Dashboard grid | Gridstack · React Grid Layout |
191
+ | Rich text | Quill |
192
+ | Code editor | Monaco Editor · CodeMirror |
193
+ | Forms | Formik + Yup |
194
+ | Drag and drop | @hello-pangea/dnd |
195
+ | Date/time | Day.js |
196
+ | Icons | Lucide React |
197
+
198
+ ---
199
+
200
+ ## Part of the SolidX Platform
201
+
202
+ `@solidxai/core-ui` is the frontend foundation of the [SolidX](https://solidxai.com) low-code development platform. It pairs with [`@solidxai/core`](https://www.npmjs.com/package/@solidxai/core) (the NestJS backend module) to form a complete full-stack framework. SolidX generates fully open-source, standards-based NestJS + React code that your team owns outright — no proprietary runtime, no lock-in.
203
+
204
+ | | |
205
+ |---|---|
206
+ | Website | [solidxai.com](https://solidxai.com) |
207
+ | Documentation | [docs.solidxai.com](https://docs.solidxai.com/docs) |
208
+ | Backend package | [@solidxai/core](https://www.npmjs.com/package/@solidxai/core) |
209
+ | Support | support@solidxai.com |
210
+
211
+ ---
212
+
213
+ ## License
214
+
215
+ BSL-1.1 © [Logicloop](https://logicloop.io)
@@ -0,0 +1,3 @@
1
+ declare const SolidOTPVerify: () => import("react/jsx-runtime").JSX.Element;
2
+ export default SolidOTPVerify;
3
+ //# sourceMappingURL=SolidOTPVerify.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"SolidOTPVerify.d.ts","sourceRoot":"./","sources":["components/auth/SolidOTPVerify.tsx"],"names":[],"mappings":"AAiBA,QAAA,MAAM,cAAc,+CAmHnB,CAAC;AAEF,eAAe,cAAc,CAAC"}
@@ -0,0 +1,67 @@
1
+ "use client";
2
+ import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
3
+ import { Form, Formik } from "formik";
4
+ import { signIn } from "next-auth/react";
5
+ import Link from "next/link";
6
+ import { useRouter } from "next/navigation";
7
+ import { Button } from "primereact/button";
8
+ import { InputOtp } from "primereact/inputotp";
9
+ import { Message } from "primereact/message";
10
+ import { Toast } from "primereact/toast";
11
+ import { useRef, useState } from "react";
12
+ import * as Yup from "yup";
13
+ import { useSelector } from "react-redux";
14
+ import Image from "next/image";
15
+ import SolidLogo from '../../resources/images/SolidXLogo.svg';
16
+ import { ERROR_MESSAGES } from "../../constants/error-messages";
17
+ const SolidOTPVerify = () => {
18
+ // const [trigger, { data: solidSettingsData }] = useLazyGetAuthSettingsQuery();
19
+ // useEffect(() => {
20
+ // trigger("") // Fetch settings on mount
21
+ // }, [trigger])
22
+ const solidSettingsData = useSelector((state) => state.settingsState?.solidSettings);
23
+ const [otp, setOTP] = useState();
24
+ const toast = useRef(null);
25
+ const router = useRouter();
26
+ const [password, setPassword] = useState('');
27
+ const [checked, setChecked] = useState(false);
28
+ const validationSchema = Yup.object({
29
+ email: Yup.string()
30
+ .email(ERROR_MESSAGES.FIELD_INVALID(' email address'))
31
+ .required(ERROR_MESSAGES.FIELD_REUQIRED('Email')),
32
+ });
33
+ const showToast = (severity, summary, detail) => {
34
+ toast.current?.show({
35
+ severity,
36
+ summary,
37
+ detail,
38
+ ...(severity === "error"
39
+ ? { sticky: true } // stays until user closes
40
+ : { life: 3000 }),
41
+ });
42
+ };
43
+ const isFormFieldValid = (formik, fieldName) => formik.touched[fieldName] && formik.errors[fieldName];
44
+ return (_jsxs(_Fragment, { children: [_jsx(Toast, { ref: toast }), _jsxs("div", { className: `auth-container ${solidSettingsData?.authPagesLayout === 'center' ? 'center' : 'side'}`, style: { minWidth: 480 }, children: [solidSettingsData?.authPagesLayout === 'center' &&
45
+ _jsx("div", { className: "flex justify-content-center", children: _jsx("div", { className: `solid-logo flex align-items-center ${solidSettingsData?.appLogoPosition}`, children: _jsx(Image, { alt: "solid logo", src: solidSettingsData?.appLogo || SolidLogo, className: "relative", fill: true }) }) }), _jsx("h2", { className: `solid-auth-title ${solidSettingsData?.authPagesLayout === 'center' ? 'text-center' : 'text-left'}`, children: "OTP Verification" }), _jsx("p", { className: "solid-auth-subtitle text-sm", children: "Please enter the OTP sent to your email to complete verification" }), _jsx(_Fragment, { children: _jsx(Formik, { initialValues: {
46
+ email: "",
47
+ password: "",
48
+ }, validationSchema: validationSchema, onSubmit: async (values) => {
49
+ // Handle form submission
50
+ const email = values.email;
51
+ const password = values.password;
52
+ const response = await signIn("credentials", {
53
+ redirect: false,
54
+ email,
55
+ password,
56
+ });
57
+ if (response?.error) {
58
+ showToast("error", ERROR_MESSAGES.LOGIN_ERROR, response.error);
59
+ }
60
+ else {
61
+ showToast("success", ERROR_MESSAGES.LOGIN_SUCCESS, ERROR_MESSAGES.DASHBOARD_REDIRECTING);
62
+ router.push(`${process.env.NEXT_PUBLIC_LOGIN_REDIRECT_URL}`);
63
+ }
64
+ }, children: (formik) => (_jsxs(Form, { children: [_jsxs("div", { className: "flex flex-column gap-2 px-3", children: [_jsx("label", { htmlFor: "email", className: "solid-auth-input-label", children: "Enter OTP" }), _jsx(InputOtp, { value: otp, onChange: (e) => setOTP(e.value), length: 6, style: { width: '100%' } }), isFormFieldValid(formik, "email") && _jsx(Message, { className: "text-red-500 text-sm", severity: "error", text: formik?.errors?.email?.toString() }), _jsxs("div", { className: "flex align-items-center justify-content-between", children: [_jsx(Button, { type: "button", icon: 'pi pi-refresh', iconPos: "left", link: true, label: "Resend Code", className: "px-0 text-sm font-normal" }), _jsx("p", { className: "m-0 text-sm text-color", children: "Time left: 00:28" })] })] }), _jsx("div", { className: "mt-4", children: _jsx(Button, { type: "submit", className: "w-full font-light auth-submit-button", label: "Verify", disabled: formik.isSubmitting, loading: formik.isSubmitting }) })] })) }) })] }), _jsx("div", { className: "text-center mt-5", children: _jsxs("div", { className: "text-sm text-400 secondary-dark-color", children: ['<', " Back to ", _jsx(Link, { className: "font-bold", href: "/auth/login", children: "Sign In" })] }) })] }));
65
+ };
66
+ export default SolidOTPVerify;
67
+ //# sourceMappingURL=SolidOTPVerify.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"SolidOTPVerify.js","sourceRoot":"./","sources":["components/auth/SolidOTPVerify.tsx"],"names":[],"mappings":"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","sourcesContent":["\"use client\";\n\nimport { Form, Formik } from \"formik\";\nimport { signIn } from \"next-auth/react\";\nimport Link from \"next/link\";\nimport { useRouter } from \"next/navigation\";\nimport { Button } from \"primereact/button\";\nimport { InputOtp } from \"primereact/inputotp\";\nimport { Message } from \"primereact/message\";\nimport { Toast } from \"primereact/toast\";\nimport { useRef, useState } from \"react\";\nimport * as Yup from \"yup\";\nimport { useSelector } from \"react-redux\";\nimport Image from \"next/image\";\nimport SolidLogo from '../../resources/images/SolidXLogo.svg'\nimport { ERROR_MESSAGES } from \"../../constants/error-messages\";\n\nconst SolidOTPVerify = () => {\n\n // const [trigger, { data: solidSettingsData }] = useLazyGetAuthSettingsQuery();\n // useEffect(() => {\n // trigger(\"\") // Fetch settings on mount\n // }, [trigger])\n\n const solidSettingsData = useSelector((state: any) => state.settingsState?.solidSettings);\n\n const [otp, setOTP] = useState<number | any>();\n\n const toast = useRef<Toast>(null);\n const router = useRouter();\n\n const [password, setPassword] = useState('');\n const [checked, setChecked] = useState<boolean>(false);\n\n const validationSchema = Yup.object({\n email: Yup.string()\n .email(ERROR_MESSAGES.FIELD_INVALID(' email address'))\n .required(ERROR_MESSAGES.FIELD_REUQIRED('Email')),\n });\n\n const showToast = (severity: \"success\" | \"error\", summary: string, detail: string) => {\n toast.current?.show({\n severity,\n summary,\n detail,\n ...(severity === \"error\"\n ? { sticky: true } // stays until user closes\n : { life: 3000 }),\n });\n };\n\n const isFormFieldValid = (formik: any, fieldName: string) =>\n formik.touched[fieldName] && formik.errors[fieldName];\n\n return (\n <>\n <Toast ref={toast} />\n <div className={`auth-container ${solidSettingsData?.authPagesLayout === 'center' ? 'center' : 'side'}`} style={{ minWidth: 480 }}>\n {solidSettingsData?.authPagesLayout === 'center' &&\n <div className=\"flex justify-content-center\">\n <div className={`solid-logo flex align-items-center ${solidSettingsData?.appLogoPosition}`}>\n <Image\n alt=\"solid logo\"\n src={solidSettingsData?.appLogo || SolidLogo}\n className=\"relative\"\n fill\n />\n </div>\n </div>\n }\n <h2 className={`solid-auth-title ${solidSettingsData?.authPagesLayout === 'center' ? 'text-center' : 'text-left'}`}>OTP Verification</h2>\n <p className=\"solid-auth-subtitle text-sm\">\n Please enter the OTP sent to your email to complete verification\n </p>\n <>\n <Formik\n initialValues={{\n email: \"\",\n password: \"\",\n }}\n validationSchema={validationSchema}\n onSubmit={async (values) => {\n // Handle form submission\n const email = values.email;\n const password = values.password;\n\n const response = await signIn(\"credentials\", {\n redirect: false,\n email,\n password,\n });\n if (response?.error) {\n showToast(\"error\", ERROR_MESSAGES.LOGIN_ERROR, response.error);\n } else {\n showToast(\"success\", ERROR_MESSAGES.LOGIN_SUCCESS, ERROR_MESSAGES.DASHBOARD_REDIRECTING);\n router.push(`${process.env.NEXT_PUBLIC_LOGIN_REDIRECT_URL}`);\n }\n\n }}\n >\n {(formik) => (\n <Form>\n <div className=\"flex flex-column gap-2 px-3\">\n <label htmlFor=\"email\" className=\"solid-auth-input-label\">Enter OTP</label>\n <InputOtp value={otp} onChange={(e) => setOTP(e.value)} length={6} style={{ width: '100%' }} />\n {isFormFieldValid(formik, \"email\") && <Message\n className=\"text-red-500 text-sm\"\n severity=\"error\"\n text={formik?.errors?.email?.toString()}\n />}\n <div className=\"flex align-items-center justify-content-between\">\n <Button type=\"button\" icon='pi pi-refresh' iconPos=\"left\" link label=\"Resend Code\" className=\"px-0 text-sm font-normal\" />\n <p className=\"m-0 text-sm text-color\">\n Time left: 00:28\n </p>\n </div>\n </div>\n <div className=\"mt-4\">\n <Button type=\"submit\" className=\"w-full font-light auth-submit-button\" label=\"Verify\" disabled={formik.isSubmitting} loading={formik.isSubmitting} />\n </div>\n </Form>\n )}\n </Formik>\n </>\n </div>\n <div className=\"text-center mt-5\">\n <div className=\"text-sm text-400 secondary-dark-color\">\n {'<'} Back to <Link className=\"font-bold\" href=\"/auth/login\">Sign In</Link>\n </div>\n </div>\n </>\n );\n};\n\nexport default SolidOTPVerify;"]}
@@ -0,0 +1,133 @@
1
+ "use client";
2
+
3
+ import { Form, Formik } from "formik";
4
+ import { signIn } from "next-auth/react";
5
+ import Link from "next/link";
6
+ import { useRouter } from "next/navigation";
7
+ import { Button } from "primereact/button";
8
+ import { InputOtp } from "primereact/inputotp";
9
+ import { Message } from "primereact/message";
10
+ import { Toast } from "primereact/toast";
11
+ import { useEffect, useRef, useState } from "react";
12
+ import * as Yup from "yup";
13
+ import Image from "next/image";
14
+ import SolidLogo from '../../resources/images/SolidXLogo.svg'
15
+ import { ERROR_MESSAGES } from "../../constants/error-messages";
16
+ import { useLazyGetAuthSettingsQuery } from "../../redux/api/solidSettingsApi";
17
+
18
+ const SolidOTPVerify = () => {
19
+
20
+ const [trigger, { data: solidSettingsData }] = useLazyGetAuthSettingsQuery();
21
+ useEffect(() => {
22
+ trigger("") // Fetch settings on mount
23
+ }, [trigger])
24
+
25
+ const [otp, setOTP] = useState<number | any>();
26
+
27
+ const toast = useRef<Toast>(null);
28
+ const router = useRouter();
29
+
30
+ const [password, setPassword] = useState('');
31
+ const [checked, setChecked] = useState<boolean>(false);
32
+
33
+ const validationSchema = Yup.object({
34
+ email: Yup.string()
35
+ .email(ERROR_MESSAGES.FIELD_INVALID(' email address'))
36
+ .required(ERROR_MESSAGES.FIELD_REUQIRED('Email')),
37
+ });
38
+
39
+ const showToast = (severity: "success" | "error", summary: string, detail: string) => {
40
+ toast.current?.show({
41
+ severity,
42
+ summary,
43
+ detail,
44
+ ...(severity === "error"
45
+ ? { sticky: true } // stays until user closes
46
+ : { life: 3000 }),
47
+ });
48
+ };
49
+
50
+ const isFormFieldValid = (formik: any, fieldName: string) =>
51
+ formik.touched[fieldName] && formik.errors[fieldName];
52
+
53
+ return (
54
+ <>
55
+ <Toast ref={toast} />
56
+ <div className={`auth-container ${solidSettingsData?.data?.authPagesLayout === 'center' ? 'center' : 'side'}`} style={{ minWidth: 480 }}>
57
+ {solidSettingsData?.data?.authPagesLayout === 'center' &&
58
+ <div className="flex justify-content-center">
59
+ <div className={`solid-logo flex align-items-center ${solidSettingsData?.data?.appLogoPosition}`}>
60
+ <Image
61
+ alt="solid logo"
62
+ src={solidSettingsData?.data?.appLogo || SolidLogo}
63
+ className="relative"
64
+ fill
65
+ />
66
+ </div>
67
+ </div>
68
+ }
69
+ <h2 className={`solid-auth-title ${solidSettingsData?.data?.authPagesLayout === 'center' ? 'text-center' : 'text-left'}`}>OTP Verification</h2>
70
+ <p className="solid-auth-subtitle text-sm">
71
+ Please enter the OTP sent to your email to complete verification
72
+ </p>
73
+ <>
74
+ <Formik
75
+ initialValues={{
76
+ email: "",
77
+ password: "",
78
+ }}
79
+ validationSchema={validationSchema}
80
+ onSubmit={async (values) => {
81
+ // Handle form submission
82
+ const email = values.email;
83
+ const password = values.password;
84
+
85
+ const response = await signIn("credentials", {
86
+ redirect: false,
87
+ email,
88
+ password,
89
+ });
90
+ if (response?.error) {
91
+ showToast("error", ERROR_MESSAGES.LOGIN_ERROR, response.error);
92
+ } else {
93
+ showToast("success", ERROR_MESSAGES.LOGIN_SUCCESS, ERROR_MESSAGES.DASHBOARD_REDIRECTING);
94
+ router.push(`${process.env.NEXT_PUBLIC_LOGIN_REDIRECT_URL}`);
95
+ }
96
+
97
+ }}
98
+ >
99
+ {(formik) => (
100
+ <Form>
101
+ <div className="flex flex-column gap-2 px-3">
102
+ <label htmlFor="email" className="solid-auth-input-label">Enter OTP</label>
103
+ <InputOtp value={otp} onChange={(e) => setOTP(e.value)} length={6} style={{ width: '100%' }} />
104
+ {isFormFieldValid(formik, "email") && <Message
105
+ className="text-red-500 text-sm"
106
+ severity="error"
107
+ text={formik?.errors?.email?.toString()}
108
+ />}
109
+ <div className="flex align-items-center justify-content-between">
110
+ <Button type="button" icon='pi pi-refresh' iconPos="left" link label="Resend Code" className="px-0 text-sm font-normal" />
111
+ <p className="m-0 text-sm text-color">
112
+ Time left: 00:28
113
+ </p>
114
+ </div>
115
+ </div>
116
+ <div className="mt-4">
117
+ <Button type="submit" className="w-full font-light auth-submit-button" label="Verify" disabled={formik.isSubmitting} loading={formik.isSubmitting} />
118
+ </div>
119
+ </Form>
120
+ )}
121
+ </Formik>
122
+ </>
123
+ </div>
124
+ <div className="text-center mt-5">
125
+ <div className="text-sm text-400 secondary-dark-color">
126
+ {'<'} Back to <Link className="font-bold" href="/auth/login">Sign In</Link>
127
+ </div>
128
+ </div>
129
+ </>
130
+ );
131
+ };
132
+
133
+ export default SolidOTPVerify;
@@ -1 +1 @@
1
- {"version":3,"file":"AuthBanner.js","sourceRoot":"","sources":["../../../src/components/common/AuthBanner.tsx"],"names":[],"mappings":";AAAA,OAAO,EAAE,GAAG,EAAE,MAAM,oBAAoB,CAAC;AAEzC,IAAM,UAAU,GAAG;IACjB,OAAO,CACL,cACE,KAAK,EAAE;YACL,QAAQ,EAAE,UAAU;YACpB,KAAK,EAAE,MAAM;YACb,MAAM,EAAE,aAAa;YACrB,UAAU,EAAE,4BAA4B;YACxC,8CAA8C;YAC9C,cAAc,EAAE,OAAO;YACvB,SAAS,EAAE,GAAG,CAAC,6BAA6B,CAAC,KAAK,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC;SAClE,EACD,SAAS,EAAC,yBAAyB,YAEnC,cAAK,SAAS,EAAC,UAAU,YACvB,eAAK,SAAS,EAAC,eAAe,aAC5B,cAAK,SAAS,EAAC,iDAAiD,YAC7D,GAAG,CAAC,iBAAiB,CAAC,GACnB,EACN,cAAK,SAAS,EAAC,kCAAkC,YAC9C,GAAG,CAAC,mCAAmC,CAAC,GACrC,EACN,cAAK,SAAS,EAAC,MAAM,GASf,IACF,GACF,GACF,CACP,CAAC;AACJ,CAAC,CAAC;AAEF,eAAe,UAAU,CAAC","sourcesContent":["import { env } from \"../../adapters/env\";\n\nconst AuthBanner = () => {\n return (\n <div\n style={{\n position: \"relative\",\n width: \"100%\",\n height: \"calc(100vh)\",\n background: 'url(/images/loginhero.png)',\n // background: 'url(/images/LoginBanner.png)',\n backgroundSize: 'cover',\n marginTop: env(\"ENABLE_CUSTOM_HEADER_FOOTER\") === \"true\" ? 70 : 0\n }}\n className=\"flex align-items-center\"\n >\n <div className=\"grid m-0\">\n <div className=\"col-8 mx-auto\">\n <div className=\"text-5xl text-white font-semibold line-height-3\">\n {env(\"SOLID_APP_TITLE\")}\n </div>\n <div className=\"text-sm text-white line-height-3\">\n {env(\"NEXT_PUBLIC_SOLID_APP_DESCRIPTION\")}\n </div>\n <div className=\"mt-5\">\n {/* <AvatarGroup>\n <Avatar image=\"/images/AvatarDemo.png\" size=\"large\" shape=\"circle\" />\n <Avatar image=\"/images/AvatarDemo.png\" size=\"large\" shape=\"circle\" />\n <Avatar image=\"/images/AvatarDemo.png\" size=\"large\" shape=\"circle\" />\n <Avatar image=\"/images/AvatarDemo.png\" size=\"large\" shape=\"circle\" />\n <Avatar image=\"/images/AvatarDemo.png\" size=\"large\" shape=\"circle\" />\n <Avatar label=\"60k+\" shape=\"circle\" size=\"large\" className=\"text-sm text-bold\" style={{ color: '#191866', backgroundColor: '#fff' }} />\n </AvatarGroup> */}\n </div>\n </div>\n </div>\n </div>\n );\n};\n\nexport default AuthBanner;\n"]}
1
+ {"version":3,"file":"AuthBanner.js","sourceRoot":"","sources":["../../../src/components/common/AuthBanner.tsx"],"names":[],"mappings":";AAAA,OAAO,EAAE,GAAG,EAAE,MAAM,oBAAoB,CAAC;AAEzC,IAAM,UAAU,GAAG;IACjB,OAAO,CACL,cACE,KAAK,EAAE;YACL,QAAQ,EAAE,UAAU;YACpB,KAAK,EAAE,MAAM;YACb,MAAM,EAAE,aAAa;YACrB,UAAU,EAAE,4BAA4B;YACxC,8CAA8C;YAC9C,cAAc,EAAE,OAAO;YACvB,SAAS,EAAE,GAAG,CAAC,6BAA6B,CAAC,KAAK,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC;SAClE,EACD,SAAS,EAAC,yBAAyB,YAEnC,cAAK,SAAS,EAAC,UAAU,YACvB,eAAK,SAAS,EAAC,eAAe,aAC5B,cAAK,SAAS,EAAC,iDAAiD,YAC7D,GAAG,CAAC,iBAAiB,CAAC,GACnB,EACN,cAAK,SAAS,EAAC,kCAAkC,YAC9C,GAAG,CAAC,mCAAmC,CAAC,GACrC,EACN,cAAK,SAAS,EAAC,MAAM,GASf,IACF,GACF,GACF,CACP,CAAC;AACJ,CAAC,CAAC;AAEF,eAAe,UAAU,CAAC"}
@@ -60,7 +60,7 @@ import { useDropzone } from 'react-dropzone';
60
60
  import { SettingDropzoneActivePlaceholder } from './SolidSettings/SettingDropzoneActivePlaceholder';
61
61
  import { SolidUploadedImage } from './SolidSettings/SolidUploadedImage';
62
62
  import { SettingsImageRemoveButton } from './SolidSettings/SettingsImageRemoveButton';
63
- import { AiModelConfigTab } from './SolidSettings/LlmSettings/AiModelConfigTab';
63
+ import { ModelConfigTab, ProvidersTab, ensureBuiltInProviders } from './SolidSettings/LlmSettings/AiModelConfigTab';
64
64
  import { useDispatch } from 'react-redux';
65
65
  import { ERROR_MESSAGES } from '../../constants/error-messages';
66
66
  import { useBulkUpdateSolidSettingsMutation, useLazyGetSolidSettingsQuery } from '../../redux/api/solidSettingsApi';
@@ -117,8 +117,8 @@ export var GeneralSettings = function () {
117
117
  var _a;
118
118
  var defaultAiConfig = {
119
119
  models: {
120
- default: { providerKey: "", behavior: { streaming: false, custom: "" } },
121
- fast: { providerKey: "", behavior: { streaming: false, custom: "" } },
120
+ default: { providerId: "", model: "", behavior: { streaming: false, custom: "" } },
121
+ fast: { providerId: "", model: "", behavior: { streaming: false, custom: "" } },
122
122
  },
123
123
  providers: {},
124
124
  };
@@ -456,35 +456,37 @@ export var GeneralSettings = function () {
456
456
  _jsx(AiSettingsSection, { aiConfig: formik.values.solidXGenAiCodeBuilderConfig, onAiConfigChange: handleAiConfigChange }), pathname.includes("api-keys") && ((_43 = session === null || session === void 0 ? void 0 : session.user) === null || _43 === void 0 ? void 0 : _43.id) &&
457
457
  _jsx(ApiKeysTab, { userId: session.user.id, canCreate: (_45 = (_44 = session === null || session === void 0 ? void 0 : session.user) === null || _44 === void 0 ? void 0 : _44.isAllowedToGenerateApiKeys) !== null && _45 !== void 0 ? _45 : false })] })] }) }) }) }));
458
458
  };
459
- var AI_TABS = [
460
- { key: "fast", label: "Fast Model", title: "Fast Model" },
461
- { key: "default", label: "Intelligent Model", title: "Intelligent Model (Reasoning & tool use)" },
462
- ];
463
459
  var DEFAULT_BEHAVIOR = { streaming: false, custom: "" };
460
+ var DEFAULT_MODEL_ENTRY = { providerId: "", model: "", behavior: DEFAULT_BEHAVIOR };
464
461
  var AiSettingsSection = function (_a) {
462
+ var _b, _c, _d, _e, _f;
465
463
  var aiConfig = _a.aiConfig, onAiConfigChange = _a.onAiConfigChange;
466
- var _b = useState("fast"), activeTab = _b[0], setActiveTab = _b[1];
467
- var tabItems = AI_TABS.map(function (tab) {
468
- var _a, _b, _c, _d, _e, _f, _g;
469
- var modelEntry = (_b = (_a = aiConfig.models) === null || _a === void 0 ? void 0 : _a[tab.key]) !== null && _b !== void 0 ? _b : { providerKey: "", behavior: DEFAULT_BEHAVIOR };
470
- var providerKey = (_c = modelEntry.providerKey) !== null && _c !== void 0 ? _c : "";
471
- var providerConfig = (_e = (_d = aiConfig.providers) === null || _d === void 0 ? void 0 : _d[providerKey]) !== null && _e !== void 0 ? _e : { provider: providerKey, apiKey: "", model: "" };
472
- var behavior = (_f = modelEntry.behavior) !== null && _f !== void 0 ? _f : DEFAULT_BEHAVIOR;
473
- return {
474
- value: tab.key,
475
- label: tab.label,
476
- content: (_jsx(AiModelConfigTab, { providerKey: providerKey, providerConfig: providerConfig, behavior: behavior, allProviders: (_g = aiConfig.providers) !== null && _g !== void 0 ? _g : {}, onProviderKeyChange: function (newKey, newConfig) {
477
- var _a, _b;
478
- onAiConfigChange(__assign(__assign({}, aiConfig), { models: __assign(__assign({}, aiConfig.models), (_a = {}, _a[tab.key] = __assign(__assign({}, modelEntry), { providerKey: newKey }), _a)), providers: __assign(__assign({}, aiConfig.providers), (_b = {}, _b[newKey] = newConfig, _b)) }));
479
- }, onProviderConfigChange: function (pk, config) {
480
- var _a;
481
- onAiConfigChange(__assign(__assign({}, aiConfig), { providers: __assign(__assign({}, aiConfig.providers), (_a = {}, _a[pk] = config, _a)) }));
482
- }, onBehaviorChange: function (newBehavior) {
483
- var _a;
484
- onAiConfigChange(__assign(__assign({}, aiConfig), { models: __assign(__assign({}, aiConfig.models), (_a = {}, _a[tab.key] = __assign(__assign({}, modelEntry), { behavior: newBehavior }), _a)) }));
464
+ var _g = useState("providers"), activeTab = _g[0], setActiveTab = _g[1];
465
+ var _h = useState(false), showAddProvider = _h[0], setShowAddProvider = _h[1];
466
+ var providers = ensureBuiltInProviders((_b = aiConfig.providers) !== null && _b !== void 0 ? _b : {});
467
+ var tabItems = [
468
+ {
469
+ value: "providers",
470
+ label: "Providers",
471
+ content: (_jsx(ProvidersTab, { providers: providers, onProvidersChange: function (newProviders) {
472
+ onAiConfigChange(__assign(__assign({}, aiConfig), { providers: newProviders }));
473
+ }, showAddModal: showAddProvider, onAddModalClose: function () { return setShowAddProvider(false); } })),
474
+ },
475
+ {
476
+ value: "default",
477
+ label: "Intelligent Model",
478
+ content: (_jsx(ModelConfigTab, { modelEntry: (_d = (_c = aiConfig.models) === null || _c === void 0 ? void 0 : _c.default) !== null && _d !== void 0 ? _d : DEFAULT_MODEL_ENTRY, providers: providers, onModelEntryChange: function (entry) {
479
+ onAiConfigChange(__assign(__assign({}, aiConfig), { models: __assign(__assign({}, aiConfig.models), { default: entry }) }));
485
480
  } })),
486
- };
487
- });
488
- return (_jsxs("div", { children: [_jsx("p", { className: "solid-settings-heading", style: { marginBottom: "1rem" }, children: "AI Model Configuration" }), _jsx(SolidTabGroup, { tabs: tabItems, value: activeTab, onValueChange: function (value) { return setActiveTab(value); }, tabPosition: "left" })] }));
481
+ },
482
+ {
483
+ value: "fast",
484
+ label: "Fast Model",
485
+ content: (_jsx(ModelConfigTab, { modelEntry: (_f = (_e = aiConfig.models) === null || _e === void 0 ? void 0 : _e.fast) !== null && _f !== void 0 ? _f : DEFAULT_MODEL_ENTRY, providers: providers, onModelEntryChange: function (entry) {
486
+ onAiConfigChange(__assign(__assign({}, aiConfig), { models: __assign(__assign({}, aiConfig.models), { fast: entry }) }));
487
+ } })),
488
+ },
489
+ ];
490
+ return (_jsxs("div", { children: [_jsx("p", { className: "solid-settings-heading", style: { marginBottom: "1rem" }, children: "AI Model Configuration" }), _jsx(SolidTabGroup, { tabs: tabItems, value: activeTab, onValueChange: function (value) { return setActiveTab(value); }, tabPosition: "left", extra: activeTab === "providers" ? (_jsx(SolidButton, { size: "sm", onClick: function () { return setShowAddProvider(true); }, children: "Add" })) : undefined })] }));
489
491
  };
490
492
  //# sourceMappingURL=GeneralSettings.js.map