@udhuong/admin-core 0.1.0 → 0.1.1
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.
- package/dist/client/auth/AuthContext.d.ts +19 -0
- package/dist/client/auth/AuthContext.d.ts.map +1 -0
- package/dist/client/auth/AuthContext.js +115 -0
- package/dist/client/auth/AuthContext.js.map +1 -0
- package/dist/client/auth/PermissionGuard.d.ts +12 -0
- package/dist/client/auth/PermissionGuard.d.ts.map +1 -0
- package/dist/client/auth/PermissionGuard.js +23 -0
- package/dist/client/auth/PermissionGuard.js.map +1 -0
- package/dist/client/auth/ProtectedPage.d.ts +9 -0
- package/dist/client/auth/ProtectedPage.d.ts.map +1 -0
- package/dist/client/auth/ProtectedPage.js +57 -0
- package/dist/client/auth/ProtectedPage.js.map +1 -0
- package/dist/client/auth/ProtectedRoute.d.ts +4 -0
- package/dist/client/auth/ProtectedRoute.d.ts.map +1 -0
- package/dist/client/auth/ProtectedRoute.js +25 -0
- package/dist/client/auth/ProtectedRoute.js.map +1 -0
- package/dist/client/auth/api-client.d.ts +4 -0
- package/dist/client/auth/api-client.d.ts.map +1 -0
- package/dist/client/auth/api-client.js +83 -0
- package/dist/client/auth/api-client.js.map +1 -0
- package/dist/client/auth/auth.service.d.ts +7 -0
- package/dist/client/auth/auth.service.d.ts.map +1 -0
- package/dist/client/auth/auth.service.js +19 -0
- package/dist/client/auth/auth.service.js.map +1 -0
- package/dist/client/auth/index.d.ts +7 -0
- package/dist/client/auth/index.d.ts.map +1 -0
- package/dist/client/auth/index.js +7 -0
- package/dist/client/auth/index.js.map +1 -0
- package/dist/client/components/PageHeader.d.ts +19 -0
- package/dist/client/components/PageHeader.d.ts.map +1 -0
- package/dist/client/components/PageHeader.js +7 -0
- package/dist/client/components/PageHeader.js.map +1 -0
- package/dist/client/components/Providers.d.ts +9 -0
- package/dist/client/components/Providers.d.ts.map +1 -0
- package/dist/client/components/Providers.js +52 -0
- package/dist/client/components/Providers.js.map +1 -0
- package/dist/client/components/ThemeToggle.d.ts +6 -0
- package/dist/client/components/ThemeToggle.d.ts.map +1 -0
- package/dist/client/components/ThemeToggle.js +22 -0
- package/dist/client/components/ThemeToggle.js.map +1 -0
- package/dist/client/components/index.d.ts +4 -0
- package/dist/client/components/index.d.ts.map +1 -0
- package/dist/client/components/index.js +4 -0
- package/dist/client/components/index.js.map +1 -0
- package/dist/client/config/AdminConfigContext.d.ts +12 -0
- package/dist/client/config/AdminConfigContext.d.ts.map +1 -0
- package/dist/client/config/AdminConfigContext.js +29 -0
- package/dist/client/config/AdminConfigContext.js.map +1 -0
- package/dist/client/config/defaults.d.ts +4 -0
- package/dist/client/config/defaults.d.ts.map +1 -0
- package/dist/client/config/defaults.js +86 -0
- package/dist/client/config/defaults.js.map +1 -0
- package/dist/client/config/types.d.ts +61 -0
- package/dist/client/config/types.d.ts.map +1 -0
- package/dist/client/config/types.js +2 -0
- package/dist/client/config/types.js.map +1 -0
- package/dist/client/constants/api-routes.d.ts +104 -0
- package/dist/client/constants/api-routes.d.ts.map +1 -0
- package/dist/client/constants/api-routes.js +91 -0
- package/dist/client/constants/api-routes.js.map +1 -0
- package/dist/client/constants/permissions.d.ts +38 -0
- package/dist/client/constants/permissions.d.ts.map +1 -0
- package/dist/client/constants/permissions.js +37 -0
- package/dist/client/constants/permissions.js.map +1 -0
- package/dist/client/contexts/ThemeContext.d.ts +3 -0
- package/dist/client/contexts/ThemeContext.d.ts.map +1 -0
- package/dist/client/contexts/ThemeContext.js +8 -0
- package/dist/client/contexts/ThemeContext.js.map +1 -0
- package/dist/client/hooks/useToast.d.ts +14 -0
- package/dist/client/hooks/useToast.d.ts.map +1 -0
- package/dist/client/hooks/useToast.js +90 -0
- package/dist/client/hooks/useToast.js.map +1 -0
- package/dist/client/index.d.ts +25 -0
- package/dist/client/index.d.ts.map +1 -0
- package/dist/client/index.js +33 -0
- package/dist/client/index.js.map +1 -0
- package/dist/client/layouts/AdminLayout.d.ts +4 -0
- package/dist/client/layouts/AdminLayout.d.ts.map +1 -0
- package/dist/client/layouts/AdminLayout.js +72 -0
- package/dist/client/layouts/AdminLayout.js.map +1 -0
- package/dist/client/layouts/Sidebar.d.ts +6 -0
- package/dist/client/layouts/Sidebar.d.ts.map +1 -0
- package/dist/client/layouts/Sidebar.js +86 -0
- package/dist/client/layouts/Sidebar.js.map +1 -0
- package/dist/client/layouts/index.d.ts +3 -0
- package/dist/client/layouts/index.d.ts.map +1 -0
- package/dist/client/layouts/index.js +3 -0
- package/dist/client/layouts/index.js.map +1 -0
- package/dist/client/lib/utils.d.ts +5 -0
- package/dist/client/lib/utils.d.ts.map +1 -0
- package/dist/client/lib/utils.js +22 -0
- package/dist/client/lib/utils.js.map +1 -0
- package/dist/client/pages/ChangePasswordPage.d.ts +2 -0
- package/dist/client/pages/ChangePasswordPage.d.ts.map +1 -0
- package/dist/client/pages/ChangePasswordPage.js +58 -0
- package/dist/client/pages/ChangePasswordPage.js.map +1 -0
- package/dist/client/pages/ForgotPasswordPage.d.ts +2 -0
- package/dist/client/pages/ForgotPasswordPage.d.ts.map +1 -0
- package/dist/client/pages/ForgotPasswordPage.js +30 -0
- package/dist/client/pages/ForgotPasswordPage.js.map +1 -0
- package/dist/client/pages/LoginPage.d.ts +2 -0
- package/dist/client/pages/LoginPage.d.ts.map +1 -0
- package/dist/client/pages/LoginPage.js +52 -0
- package/dist/client/pages/LoginPage.js.map +1 -0
- package/dist/client/pages/PermissionsPage.d.ts +2 -0
- package/dist/client/pages/PermissionsPage.d.ts.map +1 -0
- package/dist/client/pages/PermissionsPage.js +42 -0
- package/dist/client/pages/PermissionsPage.js.map +1 -0
- package/dist/client/pages/ProfilePage.d.ts +2 -0
- package/dist/client/pages/ProfilePage.d.ts.map +1 -0
- package/dist/client/pages/ProfilePage.js +107 -0
- package/dist/client/pages/ProfilePage.js.map +1 -0
- package/dist/client/pages/ResetPasswordPage.d.ts +2 -0
- package/dist/client/pages/ResetPasswordPage.d.ts.map +1 -0
- package/dist/client/pages/ResetPasswordPage.js +68 -0
- package/dist/client/pages/ResetPasswordPage.js.map +1 -0
- package/dist/client/pages/RolesPage.d.ts +2 -0
- package/dist/client/pages/RolesPage.d.ts.map +1 -0
- package/dist/client/pages/RolesPage.js +82 -0
- package/dist/client/pages/RolesPage.js.map +1 -0
- package/dist/client/pages/UnauthorizedPage.d.ts +2 -0
- package/dist/client/pages/UnauthorizedPage.d.ts.map +1 -0
- package/dist/client/pages/UnauthorizedPage.js +9 -0
- package/dist/client/pages/UnauthorizedPage.js.map +1 -0
- package/dist/client/pages/UserDetailPage.d.ts +6 -0
- package/dist/client/pages/UserDetailPage.d.ts.map +1 -0
- package/dist/client/pages/UserDetailPage.js +220 -0
- package/dist/client/pages/UserDetailPage.js.map +1 -0
- package/dist/client/pages/UserPreferencesPage.d.ts +2 -0
- package/dist/client/pages/UserPreferencesPage.d.ts.map +1 -0
- package/dist/client/pages/UserPreferencesPage.js +152 -0
- package/dist/client/pages/UserPreferencesPage.js.map +1 -0
- package/dist/client/pages/UsersPage.d.ts +2 -0
- package/dist/client/pages/UsersPage.d.ts.map +1 -0
- package/dist/client/pages/UsersPage.js +228 -0
- package/dist/client/pages/UsersPage.js.map +1 -0
- package/dist/client/pages/VerifyEmailPage.d.ts +2 -0
- package/dist/client/pages/VerifyEmailPage.d.ts.map +1 -0
- package/dist/client/pages/VerifyEmailPage.js +43 -0
- package/dist/client/pages/VerifyEmailPage.js.map +1 -0
- package/dist/client/pages/index.d.ts +13 -0
- package/dist/client/pages/index.d.ts.map +1 -0
- package/dist/client/pages/index.js +13 -0
- package/dist/client/pages/index.js.map +1 -0
- package/dist/client/pages/roles/RoleModal.d.ts +10 -0
- package/dist/client/pages/roles/RoleModal.d.ts.map +1 -0
- package/dist/client/pages/roles/RoleModal.js +123 -0
- package/dist/client/pages/roles/RoleModal.js.map +1 -0
- package/dist/client/pages/users/DangerZone.d.ts +10 -0
- package/dist/client/pages/users/DangerZone.d.ts.map +1 -0
- package/dist/client/pages/users/DangerZone.js +8 -0
- package/dist/client/pages/users/DangerZone.js.map +1 -0
- package/dist/client/pages/users/ProfileCard.d.ts +14 -0
- package/dist/client/pages/users/ProfileCard.d.ts.map +1 -0
- package/dist/client/pages/users/ProfileCard.js +8 -0
- package/dist/client/pages/users/ProfileCard.js.map +1 -0
- package/dist/client/pages/users/SecuritySection.d.ts +14 -0
- package/dist/client/pages/users/SecuritySection.d.ts.map +1 -0
- package/dist/client/pages/users/SecuritySection.js +16 -0
- package/dist/client/pages/users/SecuritySection.js.map +1 -0
- package/dist/client/pages/users/SessionsSection.d.ts +25 -0
- package/dist/client/pages/users/SessionsSection.d.ts.map +1 -0
- package/dist/client/pages/users/SessionsSection.js +93 -0
- package/dist/client/pages/users/SessionsSection.js.map +1 -0
- package/dist/client/pages/users/SocialAccountsSection.d.ts +29 -0
- package/dist/client/pages/users/SocialAccountsSection.d.ts.map +1 -0
- package/dist/client/pages/users/SocialAccountsSection.js +72 -0
- package/dist/client/pages/users/SocialAccountsSection.js.map +1 -0
- package/dist/client/pages/users/UserDetailModal.d.ts +24 -0
- package/dist/client/pages/users/UserDetailModal.d.ts.map +1 -0
- package/dist/client/pages/users/UserDetailModal.js +42 -0
- package/dist/client/pages/users/UserDetailModal.js.map +1 -0
- package/dist/client/pages/users/UserFilters.d.ts +14 -0
- package/dist/client/pages/users/UserFilters.d.ts.map +1 -0
- package/dist/client/pages/users/UserFilters.js +22 -0
- package/dist/client/pages/users/UserFilters.js.map +1 -0
- package/dist/client/pages/users/UserStats.d.ts +9 -0
- package/dist/client/pages/users/UserStats.d.ts.map +1 -0
- package/dist/client/pages/users/UserStats.js +37 -0
- package/dist/client/pages/users/UserStats.js.map +1 -0
- package/dist/client/pages/users/UserTable.d.ts +24 -0
- package/dist/client/pages/users/UserTable.d.ts.map +1 -0
- package/dist/client/pages/users/UserTable.js +39 -0
- package/dist/client/pages/users/UserTable.js.map +1 -0
- package/dist/client/pages/users/VerificationSection.d.ts +9 -0
- package/dist/client/pages/users/VerificationSection.d.ts.map +1 -0
- package/dist/client/pages/users/VerificationSection.js +8 -0
- package/dist/client/pages/users/VerificationSection.js.map +1 -0
- package/dist/client/types/auth.d.ts +29 -0
- package/dist/client/types/auth.d.ts.map +1 -0
- package/dist/client/types/auth.js +2 -0
- package/dist/client/types/auth.js.map +1 -0
- package/dist/client/types/rbac.d.ts +39 -0
- package/dist/client/types/rbac.d.ts.map +1 -0
- package/dist/client/types/rbac.js +5 -0
- package/dist/client/types/rbac.js.map +1 -0
- package/dist/client/types/status.d.ts +12 -0
- package/dist/client/types/status.d.ts.map +1 -0
- package/dist/client/types/status.js +14 -0
- package/dist/client/types/status.js.map +1 -0
- package/dist/client/ui/Badge.d.ts +14 -0
- package/dist/client/ui/Badge.d.ts.map +1 -0
- package/dist/client/ui/Badge.js +32 -0
- package/dist/client/ui/Badge.js.map +1 -0
- package/dist/client/ui/Button.d.ts +18 -0
- package/dist/client/ui/Button.d.ts.map +1 -0
- package/dist/client/ui/Button.js +33 -0
- package/dist/client/ui/Button.js.map +1 -0
- package/dist/client/ui/Checkbox.d.ts +14 -0
- package/dist/client/ui/Checkbox.d.ts.map +1 -0
- package/dist/client/ui/Checkbox.js +35 -0
- package/dist/client/ui/Checkbox.js.map +1 -0
- package/dist/client/ui/ConfirmModal.d.ts +14 -0
- package/dist/client/ui/ConfirmModal.d.ts.map +1 -0
- package/dist/client/ui/ConfirmModal.js +43 -0
- package/dist/client/ui/ConfirmModal.js.map +1 -0
- package/dist/client/ui/DataTable.d.ts +69 -0
- package/dist/client/ui/DataTable.d.ts.map +1 -0
- package/dist/client/ui/DataTable.js +133 -0
- package/dist/client/ui/DataTable.js.map +1 -0
- package/dist/client/ui/Dropdown.d.ts +11 -0
- package/dist/client/ui/Dropdown.d.ts.map +1 -0
- package/dist/client/ui/Dropdown.js +65 -0
- package/dist/client/ui/Dropdown.js.map +1 -0
- package/dist/client/ui/FileInput.d.ts +16 -0
- package/dist/client/ui/FileInput.d.ts.map +1 -0
- package/dist/client/ui/FileInput.js +45 -0
- package/dist/client/ui/FileInput.js.map +1 -0
- package/dist/client/ui/Input.d.ts +16 -0
- package/dist/client/ui/Input.d.ts.map +1 -0
- package/dist/client/ui/Input.js +33 -0
- package/dist/client/ui/Input.js.map +1 -0
- package/dist/client/ui/LoadingSpinner.d.ts +7 -0
- package/dist/client/ui/LoadingSpinner.d.ts.map +1 -0
- package/dist/client/ui/LoadingSpinner.js +12 -0
- package/dist/client/ui/LoadingSpinner.js.map +1 -0
- package/dist/client/ui/Modal.d.ts +14 -0
- package/dist/client/ui/Modal.d.ts.map +1 -0
- package/dist/client/ui/Modal.js +46 -0
- package/dist/client/ui/Modal.js.map +1 -0
- package/dist/client/ui/Pagination.d.ts +14 -0
- package/dist/client/ui/Pagination.d.ts.map +1 -0
- package/dist/client/ui/Pagination.js +50 -0
- package/dist/client/ui/Pagination.js.map +1 -0
- package/dist/client/ui/Radio.d.ts +34 -0
- package/dist/client/ui/Radio.d.ts.map +1 -0
- package/dist/client/ui/Radio.js +44 -0
- package/dist/client/ui/Radio.js.map +1 -0
- package/dist/client/ui/Range.d.ts +17 -0
- package/dist/client/ui/Range.d.ts.map +1 -0
- package/dist/client/ui/Range.js +28 -0
- package/dist/client/ui/Range.js.map +1 -0
- package/dist/client/ui/Rating.d.ts +18 -0
- package/dist/client/ui/Rating.d.ts.map +1 -0
- package/dist/client/ui/Rating.js +64 -0
- package/dist/client/ui/Rating.js.map +1 -0
- package/dist/client/ui/Select.d.ts +20 -0
- package/dist/client/ui/Select.d.ts.map +1 -0
- package/dist/client/ui/Select.js +30 -0
- package/dist/client/ui/Select.js.map +1 -0
- package/dist/client/ui/Textarea.d.ts +14 -0
- package/dist/client/ui/Textarea.d.ts.map +1 -0
- package/dist/client/ui/Textarea.js +20 -0
- package/dist/client/ui/Textarea.js.map +1 -0
- package/dist/client/ui/Toggle.d.ts +13 -0
- package/dist/client/ui/Toggle.d.ts.map +1 -0
- package/dist/client/ui/Toggle.js +29 -0
- package/dist/client/ui/Toggle.js.map +1 -0
- package/dist/client/ui/index.d.ts +31 -0
- package/dist/client/ui/index.d.ts.map +1 -0
- package/dist/client/ui/index.js +35 -0
- package/dist/client/ui/index.js.map +1 -0
- package/dist/tailwind.preset.d.ts +10 -0
- package/dist/tailwind.preset.js +12 -0
- package/package.json +46 -17
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
'use client';
|
|
2
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
3
|
+
import ThemeToggle from '../components/ThemeToggle';
|
|
4
|
+
import Button from '../ui/Button';
|
|
5
|
+
import Input from '../ui/Input';
|
|
6
|
+
import { useAuth } from '../auth/AuthContext';
|
|
7
|
+
import { useAdminConfig } from '../config/AdminConfigContext';
|
|
8
|
+
import { zodResolver } from '@hookform/resolvers/zod';
|
|
9
|
+
import { useRouter } from 'next/navigation';
|
|
10
|
+
import { useState, useEffect } from 'react';
|
|
11
|
+
import { useForm } from 'react-hook-form';
|
|
12
|
+
import { z } from 'zod';
|
|
13
|
+
const loginSchema = z.object({
|
|
14
|
+
email: z.string().email('Email không hợp lệ'),
|
|
15
|
+
password: z.string().min(6, 'Mật khẩu phải có ít nhất 6 ký tự'),
|
|
16
|
+
});
|
|
17
|
+
export default function LoginPage() {
|
|
18
|
+
const { login, isAuthenticated, loading } = useAuth();
|
|
19
|
+
const { resolvedRoutes } = useAdminConfig();
|
|
20
|
+
const router = useRouter();
|
|
21
|
+
const [error, setError] = useState('');
|
|
22
|
+
const [isLoading, setIsLoading] = useState(false);
|
|
23
|
+
useEffect(() => {
|
|
24
|
+
if (!loading && isAuthenticated) {
|
|
25
|
+
router.replace(resolvedRoutes.DASHBOARD);
|
|
26
|
+
}
|
|
27
|
+
}, [isAuthenticated, loading, router, resolvedRoutes]);
|
|
28
|
+
const { register, handleSubmit, formState: { errors }, } = useForm({
|
|
29
|
+
resolver: zodResolver(loginSchema),
|
|
30
|
+
});
|
|
31
|
+
const onSubmit = async (data) => {
|
|
32
|
+
try {
|
|
33
|
+
setIsLoading(true);
|
|
34
|
+
setError('');
|
|
35
|
+
await login(data);
|
|
36
|
+
}
|
|
37
|
+
catch (err) {
|
|
38
|
+
setError(err.response?.data?.message || 'Đăng nhập thất bại. Vui lòng thử lại.');
|
|
39
|
+
}
|
|
40
|
+
finally {
|
|
41
|
+
setIsLoading(false);
|
|
42
|
+
}
|
|
43
|
+
};
|
|
44
|
+
if (loading) {
|
|
45
|
+
return (_jsx("div", { className: "min-h-screen flex items-center justify-center bg-gradient-to-br from-base-50 to-base-100", children: _jsxs("div", { className: "text-center", children: [_jsx("div", { className: "inline-block w-8 h-8 border-4 border-base-600 border-t-transparent rounded-full animate-spin" }), _jsx("p", { className: "mt-4 text-base-600", children: "\u0110ang ki\u1EC3m tra..." })] }) }));
|
|
46
|
+
}
|
|
47
|
+
if (isAuthenticated) {
|
|
48
|
+
return null;
|
|
49
|
+
}
|
|
50
|
+
return (_jsxs("div", { className: "min-h-screen flex items-center justify-center bg-gradient-to-br from-base-50 to-base-100 px-4", children: [_jsx("div", { className: "absolute top-4 right-4", children: _jsx(ThemeToggle, {}) }), _jsx("div", { className: "w-full max-w-md", children: _jsxs("div", { className: "bg-base-100 rounded-2xl shadow-xl p-8", children: [_jsxs("div", { className: "text-center mb-8", children: [_jsx("div", { className: "inline-flex items-center justify-center w-16 h-16 bg-base-600 rounded-full mb-4", children: _jsx("svg", { className: "w-8 h-8 text-primary-100", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: _jsx("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M12 15v2m-6 4h12a2 2 0 002-2v-6a2 2 0 00-2-2H6a2 2 0 00-2 2v6a2 2 0 002 2zm10-10V7a4 4 0 00-8 0v4h8z" }) }) }), _jsx("h1", { className: "text-2xl font-bold text-base-900", children: "Admin Panel" }), _jsx("p", { className: "text-base-600 mt-2", children: "\u0110\u0103ng nh\u1EADp \u0111\u1EC3 qu\u1EA3n l\u00FD n\u1ED9i dung" })] }), error && (_jsx("div", { className: "mb-6 p-4 bg-red-50 border border-red-200 rounded-lg", children: _jsx("p", { className: "text-sm text-red-600", children: error }) })), _jsxs("form", { onSubmit: handleSubmit(onSubmit), className: "space-y-6", children: [_jsx(Input, { label: "Email", type: "email", placeholder: "admin@example.com", error: errors.email?.message, ...register('email'), autoComplete: "email" }), _jsx(Input, { label: "M\u1EADt kh\u1EA9u", type: "password", placeholder: "\u2022\u2022\u2022\u2022\u2022\u2022\u2022\u2022", error: errors.password?.message, ...register('password'), autoComplete: "current-password" }), _jsx(Button, { type: "submit", variant: "primary", size: "lg", className: "w-full", isLoading: isLoading, children: "\u0110\u0103ng nh\u1EADp" })] }), _jsx("div", { className: "mt-6 text-center", children: _jsx("p", { className: "text-sm text-base-500", children: "\u00A9 2025 Personal Profile. All rights reserved." }) })] }) })] }));
|
|
51
|
+
}
|
|
52
|
+
//# sourceMappingURL=LoginPage.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"LoginPage.js","sourceRoot":"","sources":["../../../src/client/pages/LoginPage.tsx"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"PermissionsPage.d.ts","sourceRoot":"","sources":["../../../src/client/pages/PermissionsPage.tsx"],"names":[],"mappings":"AA6BA,MAAM,CAAC,OAAO,UAAU,eAAe,4CA6JtC"}
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
'use client';
|
|
2
|
+
import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
|
|
3
|
+
import { useQuery } from '@tanstack/react-query';
|
|
4
|
+
import { Shield, ChevronDown, ChevronUp } from 'lucide-react';
|
|
5
|
+
import { useState } from 'react';
|
|
6
|
+
import { getApiClient } from '../auth/api-client';
|
|
7
|
+
import { CORE_ADMIN_API_ROUTES } from '../constants/api-routes';
|
|
8
|
+
import PageHeader from '../components/PageHeader';
|
|
9
|
+
import ProtectedPage from '../auth/ProtectedPage';
|
|
10
|
+
import { PERMISSIONS } from '../constants/permissions';
|
|
11
|
+
export default function PermissionsPage() {
|
|
12
|
+
const apiClient = getApiClient();
|
|
13
|
+
const [expandedGroups, setExpandedGroups] = useState([]);
|
|
14
|
+
// Fetch permissions
|
|
15
|
+
const { data, isLoading } = useQuery({
|
|
16
|
+
queryKey: ['permissions'],
|
|
17
|
+
queryFn: async () => {
|
|
18
|
+
const response = await apiClient.get(CORE_ADMIN_API_ROUTES.PERMISSIONS.BASE);
|
|
19
|
+
return response.data;
|
|
20
|
+
},
|
|
21
|
+
});
|
|
22
|
+
const toggleGroup = (resource) => {
|
|
23
|
+
setExpandedGroups((prev) => prev.includes(resource) ? prev.filter((r) => r !== resource) : [...prev, resource]);
|
|
24
|
+
};
|
|
25
|
+
const toggleAll = () => {
|
|
26
|
+
if (data?.grouped) {
|
|
27
|
+
if (expandedGroups.length === Object.keys(data.grouped).length) {
|
|
28
|
+
setExpandedGroups([]);
|
|
29
|
+
}
|
|
30
|
+
else {
|
|
31
|
+
setExpandedGroups(Object.keys(data.grouped));
|
|
32
|
+
}
|
|
33
|
+
}
|
|
34
|
+
};
|
|
35
|
+
return (_jsx(ProtectedPage, { permission: PERMISSIONS.ROLE_READ, children: _jsxs("div", { className: "space-y-6 p-6 bg-base-200 min-h-screen", children: [_jsx(PageHeader, { title: "Danh s\u00E1ch quy\u1EC1n h\u1EA1n", description: "T\u1EA5t c\u1EA3 c\u00E1c quy\u1EC1n trong h\u1EC7 th\u1ED1ng \u0111\u01B0\u1EE3c nh\u00F3m theo resource" }), isLoading ? (_jsx("div", { className: "text-center py-12", children: _jsx("div", { className: "loading loading-spinner loading-lg" }) })) : (_jsxs(_Fragment, { children: [_jsxs("div", { className: "stats shadow bg-base-100 w-full", children: [_jsxs("div", { className: "stat", children: [_jsx("div", { className: "stat-figure text-primary", children: _jsx(Shield, { className: "w-8 h-8" }) }), _jsx("div", { className: "stat-title", children: "T\u1ED5ng s\u1ED1 quy\u1EC1n" }), _jsx("div", { className: "stat-value text-primary", children: data?.total }), _jsxs("div", { className: "stat-desc", children: ["Nh\u00F3m theo ", Object.keys(data?.grouped || {}).length, " resource"] })] }), _jsx("div", { className: "stat", children: _jsx("div", { className: "stat-actions", children: _jsx("button", { onClick: toggleAll, className: "btn btn-sm btn-outline", children: expandedGroups.length === Object.keys(data?.grouped || {}).length
|
|
36
|
+
? 'Thu gọn tất cả'
|
|
37
|
+
: 'Mở rộng tất cả' }) }) })] }), _jsxs("div", { className: "space-y-4", children: [Object.entries(data?.grouped || {}).map(([resource, permissions]) => {
|
|
38
|
+
const isExpanded = expandedGroups.includes(resource);
|
|
39
|
+
return (_jsxs("div", { className: "card bg-base-100 shadow-sm overflow-hidden", children: [_jsxs("button", { onClick: () => toggleGroup(resource), className: "w-full px-6 py-4 flex items-center justify-between hover:bg-base-200 transition-colors", children: [_jsxs("div", { className: "flex items-center gap-3", children: [isExpanded ? (_jsx(ChevronUp, { className: "w-5 h-5 text-base-content/60" })) : (_jsx(ChevronDown, { className: "w-5 h-5 text-base-content/60" })), _jsx(Shield, { className: "w-5 h-5 text-primary" }), _jsxs("div", { className: "text-left", children: [_jsx("h3", { className: "font-semibold text-lg uppercase", children: resource }), _jsxs("p", { className: "text-sm text-base-content/60", children: [permissions.length, " quy\u1EC1n"] })] })] }), _jsx("div", { className: "flex items-center gap-2", children: _jsx("span", { className: "badge badge-primary", children: permissions.length }) })] }), isExpanded && (_jsx("div", { className: "border-t border-base-300", children: _jsx("div", { className: "grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-4 p-6", children: permissions.map((permission) => (_jsxs("div", { className: "card border border-base-300 bg-base-100 p-4 hover:shadow-md transition-shadow", children: [_jsxs("div", { className: "flex items-start justify-between mb-2", children: [_jsx("div", { className: "font-mono text-sm font-medium text-primary", children: permission.name }), _jsx("span", { className: "badge badge-ghost text-xs", children: permission.action })] }), permission.description && (_jsx("p", { className: "text-sm text-base-content/60 mt-2", children: permission.description })), _jsx("div", { className: "mt-3 pt-3 border-t border-base-300", children: _jsxs("span", { className: "text-xs text-base-content/50", children: ["ID: ", permission.id] }) })] }, permission.id))) }) }))] }, resource));
|
|
40
|
+
}), Object.keys(data?.grouped || {}).length === 0 && (_jsxs("div", { className: "text-center py-12", children: [_jsx(Shield, { className: "w-12 h-12 text-base-content/40 mx-auto mb-4" }), _jsx("p", { className: "text-base-content/60", children: "Kh\u00F4ng c\u00F3 quy\u1EC1n n\u00E0o trong h\u1EC7 th\u1ED1ng" })] }))] })] }))] }) }));
|
|
41
|
+
}
|
|
42
|
+
//# sourceMappingURL=PermissionsPage.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"PermissionsPage.js","sourceRoot":"","sources":["../../../src/client/pages/PermissionsPage.tsx"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ProfilePage.d.ts","sourceRoot":"","sources":["../../../src/client/pages/ProfilePage.tsx"],"names":[],"mappings":"AAYA,MAAM,CAAC,OAAO,UAAU,WAAW,4CA+ZlC"}
|
|
@@ -0,0 +1,107 @@
|
|
|
1
|
+
'use client';
|
|
2
|
+
import { jsx as _jsx, Fragment as _Fragment, jsxs as _jsxs } from "react/jsx-runtime";
|
|
3
|
+
import PageHeader from '../components/PageHeader';
|
|
4
|
+
import { useAuth } from '../auth/AuthContext';
|
|
5
|
+
import { useState } from 'react';
|
|
6
|
+
import { Camera, Mail, User as UserIcon, Save, Calendar, Shield, CheckCircle, XCircle, Eye, EyeOff } from 'lucide-react';
|
|
7
|
+
import { useMutation } from '@tanstack/react-query';
|
|
8
|
+
import { getApiClient } from '../auth/api-client';
|
|
9
|
+
import { CORE_API_ROUTES } from '../constants/api-routes';
|
|
10
|
+
import { useToast } from '../hooks/useToast';
|
|
11
|
+
import { useAdminConfig } from '../config/AdminConfigContext';
|
|
12
|
+
export default function ProfilePage() {
|
|
13
|
+
const apiClient = getApiClient();
|
|
14
|
+
const { user, refreshProfile } = useAuth();
|
|
15
|
+
const { showToast } = useToast();
|
|
16
|
+
const { renderAvatarPicker } = useAdminConfig();
|
|
17
|
+
const [isEditing, setIsEditing] = useState(false);
|
|
18
|
+
// Form state
|
|
19
|
+
const [formData, setFormData] = useState({
|
|
20
|
+
displayName: user?.displayName || '',
|
|
21
|
+
username: user?.username || '',
|
|
22
|
+
email: user?.email || '',
|
|
23
|
+
avatar: user?.avatar || '',
|
|
24
|
+
});
|
|
25
|
+
// Password change state
|
|
26
|
+
const [passwordData, setPasswordData] = useState({
|
|
27
|
+
currentPassword: '',
|
|
28
|
+
newPassword: '',
|
|
29
|
+
confirmPassword: '',
|
|
30
|
+
});
|
|
31
|
+
const [showPasswords, setShowPasswords] = useState({
|
|
32
|
+
current: false,
|
|
33
|
+
new: false,
|
|
34
|
+
confirm: false,
|
|
35
|
+
});
|
|
36
|
+
// Update profile mutation
|
|
37
|
+
const updateProfileMutation = useMutation({
|
|
38
|
+
mutationFn: async (data) => {
|
|
39
|
+
const response = await apiClient.patch(CORE_API_ROUTES.AUTH.PROFILE, data);
|
|
40
|
+
return response.data;
|
|
41
|
+
},
|
|
42
|
+
onSuccess: () => {
|
|
43
|
+
showToast('Profile updated successfully', 'success');
|
|
44
|
+
refreshProfile();
|
|
45
|
+
setIsEditing(false);
|
|
46
|
+
},
|
|
47
|
+
onError: (error) => {
|
|
48
|
+
showToast(error?.response?.data?.message || 'Failed to update profile', 'error');
|
|
49
|
+
},
|
|
50
|
+
});
|
|
51
|
+
// Change password mutation
|
|
52
|
+
const changePasswordMutation = useMutation({
|
|
53
|
+
mutationFn: async (data) => {
|
|
54
|
+
const response = await apiClient.post(CORE_API_ROUTES.AUTH.CHANGE_PASSWORD, {
|
|
55
|
+
currentPassword: data.currentPassword,
|
|
56
|
+
newPassword: data.newPassword,
|
|
57
|
+
});
|
|
58
|
+
return response.data;
|
|
59
|
+
},
|
|
60
|
+
onSuccess: () => {
|
|
61
|
+
showToast('Password changed successfully', 'success');
|
|
62
|
+
setPasswordData({ currentPassword: '', newPassword: '', confirmPassword: '' });
|
|
63
|
+
},
|
|
64
|
+
onError: (error) => {
|
|
65
|
+
showToast(error?.response?.data?.message || 'Failed to change password', 'error');
|
|
66
|
+
},
|
|
67
|
+
});
|
|
68
|
+
const handleSaveProfile = () => {
|
|
69
|
+
updateProfileMutation.mutate(formData);
|
|
70
|
+
};
|
|
71
|
+
const handleCancelEdit = () => {
|
|
72
|
+
setFormData({
|
|
73
|
+
displayName: user?.displayName || '',
|
|
74
|
+
username: user?.username || '',
|
|
75
|
+
email: user?.email || '',
|
|
76
|
+
avatar: user?.avatar || '',
|
|
77
|
+
});
|
|
78
|
+
setIsEditing(false);
|
|
79
|
+
};
|
|
80
|
+
const handleChangePassword = () => {
|
|
81
|
+
if (passwordData.newPassword !== passwordData.confirmPassword) {
|
|
82
|
+
showToast('Passwords do not match', 'error');
|
|
83
|
+
return;
|
|
84
|
+
}
|
|
85
|
+
if (passwordData.newPassword.length < 8) {
|
|
86
|
+
showToast('Password must be at least 8 characters', 'error');
|
|
87
|
+
return;
|
|
88
|
+
}
|
|
89
|
+
changePasswordMutation.mutate(passwordData);
|
|
90
|
+
};
|
|
91
|
+
const handleAvatarUrlChange = (url) => {
|
|
92
|
+
setFormData(prev => ({ ...prev, avatar: url }));
|
|
93
|
+
};
|
|
94
|
+
return (_jsxs("div", { className: "p-6 max-w-7xl mx-auto", children: [_jsx(PageHeader, { title: "My Profile" }), _jsxs("div", { className: "mt-6 grid grid-cols-1 lg:grid-cols-3 gap-6", children: [_jsx("div", { className: "lg:col-span-1", children: _jsx("div", { className: "card bg-base-100", children: _jsxs("div", { className: "card-body items-center text-center", children: [_jsxs("div", { className: "relative group mb-4", children: [_jsx("div", { className: "w-32 h-32 rounded-full bg-base-300 overflow-hidden flex items-center justify-center", children: formData.avatar ? (_jsx("img", { src: formData.avatar, alt: "Avatar", width: 128, height: 128, className: "w-full h-full object-cover" })) : (_jsx("span", { className: "text-4xl font-bold text-base-content/30", children: formData.displayName?.charAt(0).toUpperCase() ||
|
|
95
|
+
formData.username?.charAt(0).toUpperCase() ||
|
|
96
|
+
formData.email?.charAt(0).toUpperCase() || 'U' })) }), isEditing && (_jsxs(_Fragment, { children: [_jsx("div", { className: "absolute inset-0 rounded-full bg-black/40 flex items-center justify-center opacity-0 group-hover:opacity-100 transition-all duration-200", children: _jsx(Camera, { className: "w-8 h-8 text-white" }) }), _jsx("div", { className: "absolute bottom-0 right-2 w-8 h-8 bg-primary rounded-full flex items-center justify-center border-2 border-base-100", children: _jsx(Camera, { className: "w-4 h-4 text-primary-content" }) })] }))] }), isEditing && (_jsx("div", { className: "w-full mt-2", children: renderAvatarPicker ? (renderAvatarPicker({
|
|
97
|
+
currentAvatar: formData.avatar,
|
|
98
|
+
onSelect: handleAvatarUrlChange,
|
|
99
|
+
})) : (_jsxs("div", { className: "form-control", children: [_jsx("label", { className: "label", children: _jsx("span", { className: "label-text text-sm", children: "Avatar URL" }) }), _jsx("input", { type: "text", value: formData.avatar, onChange: (e) => handleAvatarUrlChange(e.target.value), className: "input input-bordered input-sm w-full", placeholder: "https://example.com/avatar.jpg" })] })) })), _jsx("h2", { className: "card-title text-2xl", children: user?.displayName || user?.username || 'User' }), _jsx("p", { className: "text-base-content/70", children: user?.email }), _jsx("div", { className: "divider my-4" }), _jsxs("div", { className: "w-full space-y-2 text-sm", children: [_jsxs("div", { className: "flex items-center justify-between", children: [_jsx("span", { className: "text-base-content/70", children: "Email Status" }), user?.emailVerified ? (_jsxs("div", { className: "badge badge-success gap-1", children: [_jsx(CheckCircle, { className: "w-3 h-3" }), "Verified"] })) : (_jsxs("div", { className: "badge badge-warning gap-1", children: [_jsx(XCircle, { className: "w-3 h-3" }), "Not Verified"] }))] }), _jsxs("div", { className: "flex items-center justify-between", children: [_jsx("span", { className: "text-base-content/70", children: "2FA" }), user?.twoFactorEnabled ? (_jsxs("div", { className: "badge badge-success gap-1", children: [_jsx(Shield, { className: "w-3 h-3" }), "Enabled"] })) : (_jsx("div", { className: "badge badge-ghost gap-1", children: "Disabled" }))] }), user?.lastLoginAt && (_jsxs("div", { className: "flex items-center justify-between", children: [_jsx("span", { className: "text-base-content/70", children: "Last Login" }), _jsx("span", { className: "text-base-content/90", children: new Date(user.lastLoginAt).toLocaleDateString() })] }))] })] }) }) }), _jsxs("div", { className: "lg:col-span-2 space-y-6", children: [_jsx("div", { className: "card bg-base-100", children: _jsxs("div", { className: "card-body", children: [_jsxs("div", { className: "flex items-center justify-between mb-4", children: [_jsx("h3", { className: "card-title", children: "Personal Information" }), !isEditing ? (_jsx("button", { onClick: () => setIsEditing(true), className: "btn btn-primary btn-sm", children: "Edit Profile" })) : (_jsxs("div", { className: "flex gap-2", children: [_jsx("button", { onClick: handleCancelEdit, className: "btn btn-ghost btn-sm", disabled: updateProfileMutation.isPending, children: "Cancel" }), _jsxs("button", { onClick: handleSaveProfile, className: "btn btn-primary btn-sm gap-2", disabled: updateProfileMutation.isPending, children: [updateProfileMutation.isPending ? (_jsx("span", { className: "loading loading-spinner loading-xs" })) : (_jsx(Save, { className: "w-4 h-4" })), "Save"] })] }))] }), _jsxs("div", { className: "grid grid-cols-1 md:grid-cols-2 gap-4", children: [_jsxs("div", { className: "form-control", children: [_jsx("label", { className: "label", children: _jsx("span", { className: "label-text font-medium", children: "Display Name" }) }), _jsxs("div", { className: "relative", children: [_jsx(UserIcon, { className: "absolute left-3 top-1/2 -translate-y-1/2 w-4 h-4 text-base-content/40 z-10" }), _jsx("input", { type: "text", value: formData.displayName, onChange: (e) => setFormData(prev => ({ ...prev, displayName: e.target.value })), disabled: !isEditing, className: "input input-bordered w-full pl-10", placeholder: "Enter display name" })] })] }), _jsxs("div", { className: "form-control", children: [_jsx("label", { className: "label", children: _jsx("span", { className: "label-text font-medium", children: "Username" }) }), _jsxs("div", { className: "relative", children: [_jsx(UserIcon, { className: "absolute left-3 top-1/2 -translate-y-1/2 w-4 h-4 text-base-content/40 z-10" }), _jsx("input", { type: "text", value: formData.username, onChange: (e) => setFormData(prev => ({ ...prev, username: e.target.value })), disabled: !isEditing, className: "input input-bordered w-full pl-10", placeholder: "Enter username" })] })] }), _jsxs("div", { className: "form-control md:col-span-2", children: [_jsx("label", { className: "label", children: _jsx("span", { className: "label-text font-medium", children: "Email" }) }), _jsxs("div", { className: "relative", children: [_jsx(Mail, { className: "absolute left-3 top-1/2 -translate-y-1/2 w-4 h-4 text-base-content/40 z-10" }), _jsx("input", { type: "email", value: formData.email, onChange: (e) => setFormData(prev => ({ ...prev, email: e.target.value })), disabled: !isEditing, className: "input input-bordered w-full pl-10", placeholder: "email@example.com" })] })] })] }), user?.createdAt && (_jsx("div", { className: "mt-4 pt-4 border-t border-base-300", children: _jsxs("div", { className: "flex items-center gap-2 text-sm text-base-content/70", children: [_jsx(Calendar, { className: "w-4 h-4" }), _jsxs("span", { children: ["Member since ", new Date(user.createdAt).toLocaleDateString('en-US', {
|
|
100
|
+
month: 'long',
|
|
101
|
+
year: 'numeric'
|
|
102
|
+
})] })] }) }))] }) }), _jsx("div", { className: "card bg-base-100 shadow-xl", children: _jsxs("div", { className: "card-body", children: [_jsx("h3", { className: "card-title mb-4", children: "Security & Password" }), _jsxs("div", { className: "space-y-4", children: [_jsxs("div", { className: "form-control", children: [_jsx("label", { className: "label", children: _jsx("span", { className: "label-text font-medium", children: "Current Password" }) }), _jsxs("div", { className: "relative", children: [_jsx("input", { type: showPasswords.current ? 'text' : 'password', value: passwordData.currentPassword, onChange: (e) => setPasswordData(prev => ({ ...prev, currentPassword: e.target.value })), className: "input input-bordered w-full pr-10", placeholder: "Enter current password" }), _jsx("button", { type: "button", onClick: () => setShowPasswords(prev => ({ ...prev, current: !prev.current })), className: "absolute right-3 top-1/2 -translate-y-1/2 text-base-content/40 hover:text-base-content", children: showPasswords.current ? _jsx(EyeOff, { className: "w-4 h-4" }) : _jsx(Eye, { className: "w-4 h-4" }) })] })] }), _jsxs("div", { className: "grid grid-cols-1 md:grid-cols-2 gap-4", children: [_jsxs("div", { className: "form-control", children: [_jsx("label", { className: "label", children: _jsx("span", { className: "label-text font-medium", children: "New Password" }) }), _jsxs("div", { className: "relative", children: [_jsx("input", { type: showPasswords.new ? 'text' : 'password', value: passwordData.newPassword, onChange: (e) => setPasswordData(prev => ({ ...prev, newPassword: e.target.value })), className: "input input-bordered w-full pr-10", placeholder: "Enter new password" }), _jsx("button", { type: "button", onClick: () => setShowPasswords(prev => ({ ...prev, new: !prev.new })), className: "absolute right-3 top-1/2 -translate-y-1/2 text-base-content/40 hover:text-base-content", children: showPasswords.new ? _jsx(EyeOff, { className: "w-4 h-4" }) : _jsx(Eye, { className: "w-4 h-4" }) })] })] }), _jsxs("div", { className: "form-control", children: [_jsx("label", { className: "label", children: _jsx("span", { className: "label-text font-medium", children: "Confirm Password" }) }), _jsxs("div", { className: "relative", children: [_jsx("input", { type: showPasswords.confirm ? 'text' : 'password', value: passwordData.confirmPassword, onChange: (e) => setPasswordData(prev => ({ ...prev, confirmPassword: e.target.value })), className: "input input-bordered w-full pr-10", placeholder: "Confirm new password" }), _jsx("button", { type: "button", onClick: () => setShowPasswords(prev => ({ ...prev, confirm: !prev.confirm })), className: "absolute right-3 top-1/2 -translate-y-1/2 text-base-content/40 hover:text-base-content", children: showPasswords.confirm ? _jsx(EyeOff, { className: "w-4 h-4" }) : _jsx(Eye, { className: "w-4 h-4" }) })] })] })] }), _jsx("div", { className: 'flex justify-end', children: _jsx("button", { onClick: handleChangePassword, disabled: !passwordData.currentPassword ||
|
|
103
|
+
!passwordData.newPassword ||
|
|
104
|
+
!passwordData.confirmPassword ||
|
|
105
|
+
changePasswordMutation.isPending, className: "btn btn-primary", children: changePasswordMutation.isPending ? (_jsx("span", { className: "loading loading-spinner loading-sm" })) : ('Change Password') }) })] })] }) })] })] })] }));
|
|
106
|
+
}
|
|
107
|
+
//# sourceMappingURL=ProfilePage.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ProfilePage.js","sourceRoot":"","sources":["../../../src/client/pages/ProfilePage.tsx"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ResetPasswordPage.d.ts","sourceRoot":"","sources":["../../../src/client/pages/ResetPasswordPage.tsx"],"names":[],"mappings":"AA2LA,MAAM,CAAC,OAAO,UAAU,iBAAiB,4CAUxC"}
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
'use client';
|
|
2
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
3
|
+
import { Suspense, useEffect, useState } from 'react';
|
|
4
|
+
import { useRouter, useSearchParams } from 'next/navigation';
|
|
5
|
+
import { useAdminConfig } from '../config/AdminConfigContext';
|
|
6
|
+
import { authService } from '../auth/auth.service';
|
|
7
|
+
import { RequestStatus } from '../types/status';
|
|
8
|
+
function ResetPasswordForm() {
|
|
9
|
+
const { resolvedRoutes } = useAdminConfig();
|
|
10
|
+
const router = useRouter();
|
|
11
|
+
const searchParams = useSearchParams();
|
|
12
|
+
const [token, setToken] = useState(null);
|
|
13
|
+
const [password, setPassword] = useState('');
|
|
14
|
+
const [confirmPassword, setConfirmPassword] = useState('');
|
|
15
|
+
const [status, setStatus] = useState(RequestStatus.IDLE);
|
|
16
|
+
const [message, setMessage] = useState('');
|
|
17
|
+
useEffect(() => {
|
|
18
|
+
const tokenParam = searchParams.get('token');
|
|
19
|
+
if (!tokenParam) {
|
|
20
|
+
setStatus(RequestStatus.ERROR);
|
|
21
|
+
setMessage('Token không hợp lệ');
|
|
22
|
+
}
|
|
23
|
+
else {
|
|
24
|
+
setToken(tokenParam);
|
|
25
|
+
}
|
|
26
|
+
}, [searchParams]);
|
|
27
|
+
const handleSubmit = async (e) => {
|
|
28
|
+
e.preventDefault();
|
|
29
|
+
if (password !== confirmPassword) {
|
|
30
|
+
setStatus(RequestStatus.ERROR);
|
|
31
|
+
setMessage('Mật khẩu xác nhận không khớp');
|
|
32
|
+
return;
|
|
33
|
+
}
|
|
34
|
+
if (password.length < 6) {
|
|
35
|
+
setStatus(RequestStatus.ERROR);
|
|
36
|
+
setMessage('Mật khẩu phải có ít nhất 6 ký tự');
|
|
37
|
+
return;
|
|
38
|
+
}
|
|
39
|
+
if (!token) {
|
|
40
|
+
setStatus(RequestStatus.ERROR);
|
|
41
|
+
setMessage('Token không hợp lệ');
|
|
42
|
+
return;
|
|
43
|
+
}
|
|
44
|
+
setStatus(RequestStatus.LOADING);
|
|
45
|
+
setMessage('');
|
|
46
|
+
try {
|
|
47
|
+
await authService.resetPassword(token, password);
|
|
48
|
+
setStatus(RequestStatus.SUCCESS);
|
|
49
|
+
setMessage('Đặt lại mật khẩu thành công!');
|
|
50
|
+
// Redirect to login after 2 seconds
|
|
51
|
+
setTimeout(() => {
|
|
52
|
+
router.push(resolvedRoutes.LOGIN);
|
|
53
|
+
}, 2000);
|
|
54
|
+
}
|
|
55
|
+
catch (error) {
|
|
56
|
+
setStatus(RequestStatus.ERROR);
|
|
57
|
+
setMessage(error.response?.data?.message || 'Đặt lại mật khẩu thất bại. Token có thể đã hết hạn.');
|
|
58
|
+
}
|
|
59
|
+
};
|
|
60
|
+
if (!token && status === RequestStatus.ERROR) {
|
|
61
|
+
return (_jsx("div", { className: "min-h-screen flex items-center justify-center bg-base-200 px-4", children: _jsx("div", { className: "card w-full max-w-md bg-base-100 shadow-xl", children: _jsxs("div", { className: "card-body text-center", children: [_jsx("div", { className: "mx-auto flex items-center justify-center h-12 w-12 rounded-full bg-error/20", children: _jsx("svg", { className: "h-6 w-6 text-error", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: _jsx("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: "2", d: "M6 18L18 6M6 6l12 12" }) }) }), _jsx("h2", { className: "card-title text-2xl justify-center mt-4", children: "Token kh\u00F4ng h\u1EE3p l\u1EC7" }), _jsx("p", { className: "text-base-content/70", children: message }), _jsx("div", { className: "card-actions justify-center mt-4", children: _jsx("button", { onClick: () => router.push(resolvedRoutes.FORGOT_PASSWORD), className: "btn btn-primary", children: "Y\u00EAu c\u1EA7u link m\u1EDBi" }) })] }) }) }));
|
|
62
|
+
}
|
|
63
|
+
return (_jsx("div", { className: "min-h-screen flex items-center justify-center bg-base-200 px-4", children: _jsx("div", { className: "card w-full max-w-md bg-base-100 shadow-xl", children: _jsxs("div", { className: "card-body", children: [_jsx("h2", { className: "card-title text-3xl justify-center", children: "\u0110\u1EB7t l\u1EA1i m\u1EADt kh\u1EA9u" }), _jsx("p", { className: "text-center text-base-content/70", children: "Nh\u1EADp m\u1EADt kh\u1EA9u m\u1EDBi c\u1EE7a b\u1EA1n" }), status === RequestStatus.SUCCESS ? (_jsxs("div", { className: "alert alert-success mt-4", children: [_jsx("svg", { xmlns: "http://www.w3.org/2000/svg", className: "stroke-current shrink-0 h-6 w-6", fill: "none", viewBox: "0 0 24 24", children: _jsx("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: "2", d: "M9 12l2 2 4-4m6 2a9 9 0 11-18 0 9 9 0 0118 0z" }) }), _jsxs("div", { children: [_jsx("div", { children: message }), _jsx("div", { className: "text-sm", children: "\u0110ang chuy\u1EC3n h\u01B0\u1EDBng \u0111\u1EBFn trang \u0111\u0103ng nh\u1EADp..." })] })] })) : (_jsxs("form", { onSubmit: handleSubmit, className: "mt-4", children: [status === RequestStatus.ERROR && (_jsxs("div", { className: "alert alert-error mb-4", children: [_jsx("svg", { xmlns: "http://www.w3.org/2000/svg", className: "stroke-current shrink-0 h-6 w-6", fill: "none", viewBox: "0 0 24 24", children: _jsx("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: "2", d: "M10 14l2-2m0 0l2-2m-2 2l-2-2m2 2l2 2m7-2a9 9 0 11-18 0 9 9 0 0118 0z" }) }), _jsx("span", { children: message })] })), _jsxs("div", { className: "form-control", children: [_jsx("label", { className: "label", htmlFor: "password", children: _jsx("span", { className: "label-text", children: "M\u1EADt kh\u1EA9u m\u1EDBi" }) }), _jsx("input", { id: "password", name: "password", type: "password", required: true, value: password, onChange: (e) => setPassword(e.target.value), className: "input input-bordered w-full", placeholder: "Nh\u1EADp m\u1EADt kh\u1EA9u m\u1EDBi", minLength: 6 })] }), _jsxs("div", { className: "form-control mt-4", children: [_jsx("label", { className: "label", htmlFor: "confirmPassword", children: _jsx("span", { className: "label-text", children: "X\u00E1c nh\u1EADn m\u1EADt kh\u1EA9u" }) }), _jsx("input", { id: "confirmPassword", name: "confirmPassword", type: "password", required: true, value: confirmPassword, onChange: (e) => setConfirmPassword(e.target.value), className: "input input-bordered w-full", placeholder: "Nh\u1EADp l\u1EA1i m\u1EADt kh\u1EA9u m\u1EDBi", minLength: 6 })] }), _jsx("div", { className: "form-control mt-6", children: _jsxs("button", { type: "submit", disabled: status === RequestStatus.LOADING, className: "btn btn-primary w-full", children: [status === RequestStatus.LOADING && _jsx("span", { className: "loading loading-spinner" }), status === RequestStatus.LOADING ? 'Đang xử lý...' : 'Đặt lại mật khẩu'] }) }), _jsx("div", { className: "text-center mt-4", children: _jsx("button", { type: "button", onClick: () => router.push(resolvedRoutes.LOGIN), className: "link link-primary text-sm", children: "\u2190 V\u1EC1 trang \u0111\u0103ng nh\u1EADp" }) })] }))] }) }) }));
|
|
64
|
+
}
|
|
65
|
+
export default function ResetPasswordPage() {
|
|
66
|
+
return (_jsx(Suspense, { fallback: _jsx("div", { className: "min-h-screen flex items-center justify-center bg-base-200", children: _jsx("div", { className: "loading loading-spinner loading-lg" }) }), children: _jsx(ResetPasswordForm, {}) }));
|
|
67
|
+
}
|
|
68
|
+
//# sourceMappingURL=ResetPasswordPage.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ResetPasswordPage.js","sourceRoot":"","sources":["../../../src/client/pages/ResetPasswordPage.tsx"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"RolesPage.d.ts","sourceRoot":"","sources":["../../../src/client/pages/RolesPage.tsx"],"names":[],"mappings":"AAeA,MAAM,CAAC,OAAO,UAAU,SAAS,4CAuOhC"}
|
|
@@ -0,0 +1,82 @@
|
|
|
1
|
+
'use client';
|
|
2
|
+
import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
|
|
3
|
+
import { useState } from 'react';
|
|
4
|
+
import { useQuery, useMutation, useQueryClient } from '@tanstack/react-query';
|
|
5
|
+
import { Plus, Edit, Trash2, Shield, Search } from 'lucide-react';
|
|
6
|
+
import { getApiClient } from '../auth/api-client';
|
|
7
|
+
import { CORE_ADMIN_API_ROUTES } from '../constants/api-routes';
|
|
8
|
+
import PageHeader from '../components/PageHeader';
|
|
9
|
+
import { ConfirmModal } from '../ui/ConfirmModal';
|
|
10
|
+
import { useToast } from '../hooks/useToast';
|
|
11
|
+
import RoleModal from './roles/RoleModal';
|
|
12
|
+
import ProtectedPage from '../auth/ProtectedPage';
|
|
13
|
+
import { PERMISSIONS } from '../constants/permissions';
|
|
14
|
+
export default function RolesPage() {
|
|
15
|
+
const apiClient = getApiClient();
|
|
16
|
+
const [searchTerm, setSearchTerm] = useState('');
|
|
17
|
+
const [currentPage, setCurrentPage] = useState(1);
|
|
18
|
+
const [isRoleModalOpen, setIsRoleModalOpen] = useState(false);
|
|
19
|
+
const [selectedRole, setSelectedRole] = useState(null);
|
|
20
|
+
const [deleteConfirmOpen, setDeleteConfirmOpen] = useState(false);
|
|
21
|
+
const [roleToDelete, setRoleToDelete] = useState(null);
|
|
22
|
+
const queryClient = useQueryClient();
|
|
23
|
+
const { showToast } = useToast();
|
|
24
|
+
// Fetch roles
|
|
25
|
+
const { data, isLoading } = useQuery({
|
|
26
|
+
queryKey: ['roles', currentPage, searchTerm],
|
|
27
|
+
queryFn: async () => {
|
|
28
|
+
const params = new URLSearchParams({
|
|
29
|
+
page: currentPage.toString(),
|
|
30
|
+
limit: '10',
|
|
31
|
+
...(searchTerm && { search: searchTerm }),
|
|
32
|
+
});
|
|
33
|
+
const response = await apiClient.get(`${CORE_ADMIN_API_ROUTES.ROLES.BASE}?${params}`);
|
|
34
|
+
return response.data;
|
|
35
|
+
},
|
|
36
|
+
});
|
|
37
|
+
// Delete mutation
|
|
38
|
+
const deleteMutation = useMutation({
|
|
39
|
+
mutationFn: async (id) => {
|
|
40
|
+
return apiClient.delete(CORE_ADMIN_API_ROUTES.ROLES.BY_ID(id));
|
|
41
|
+
},
|
|
42
|
+
onSuccess: () => {
|
|
43
|
+
showToast('Xóa vai trò thành công', 'success');
|
|
44
|
+
queryClient.invalidateQueries({ queryKey: ['roles'] });
|
|
45
|
+
setDeleteConfirmOpen(false);
|
|
46
|
+
setRoleToDelete(null);
|
|
47
|
+
},
|
|
48
|
+
onError: (error) => {
|
|
49
|
+
showToast(error.response?.data?.message || 'Xóa vai trò thất bại', 'error');
|
|
50
|
+
},
|
|
51
|
+
});
|
|
52
|
+
const handleEdit = (role) => {
|
|
53
|
+
setSelectedRole(role);
|
|
54
|
+
setIsRoleModalOpen(true);
|
|
55
|
+
};
|
|
56
|
+
const handleCreate = () => {
|
|
57
|
+
setSelectedRole(null);
|
|
58
|
+
setIsRoleModalOpen(true);
|
|
59
|
+
};
|
|
60
|
+
const handleDelete = (role) => {
|
|
61
|
+
setRoleToDelete(role);
|
|
62
|
+
setDeleteConfirmOpen(true);
|
|
63
|
+
};
|
|
64
|
+
const confirmDelete = () => {
|
|
65
|
+
if (roleToDelete) {
|
|
66
|
+
deleteMutation.mutate(roleToDelete.id);
|
|
67
|
+
}
|
|
68
|
+
};
|
|
69
|
+
const handleRoleModalClose = () => {
|
|
70
|
+
setIsRoleModalOpen(false);
|
|
71
|
+
setSelectedRole(null);
|
|
72
|
+
};
|
|
73
|
+
const handleRoleSuccess = () => {
|
|
74
|
+
queryClient.invalidateQueries({ queryKey: ['roles'] });
|
|
75
|
+
handleRoleModalClose();
|
|
76
|
+
};
|
|
77
|
+
return (_jsx(ProtectedPage, { permission: PERMISSIONS.ROLE_READ, children: _jsxs("div", { className: "space-y-6 p-6 bg-base-200 min-h-screen", children: [_jsx(PageHeader, { title: "Qu\u1EA3n l\u00FD vai tr\u00F2", description: "Qu\u1EA3n l\u00FD vai tr\u00F2 v\u00E0 ph\u00E2n quy\u1EC1n trong h\u1EC7 th\u1ED1ng" }), _jsxs("div", { className: "flex justify-between items-center mb-6", children: [_jsxs("div", { className: "relative flex-1 max-w-md", children: [_jsx(Search, { className: "absolute left-3 top-1/2 transform -translate-y-1/2 text-base-content/60 w-4 h-4" }), _jsx("input", { type: "text", placeholder: "T\u00ECm ki\u1EBFm vai tr\u00F2...", value: searchTerm, onChange: (e) => {
|
|
78
|
+
setSearchTerm(e.target.value);
|
|
79
|
+
setCurrentPage(1);
|
|
80
|
+
}, className: "input input-bordered w-full pl-10" })] }), _jsxs("button", { onClick: handleCreate, className: "btn btn-primary ml-4", children: [_jsx(Plus, { className: "w-4 h-4" }), "Th\u00EAm vai tr\u00F2"] })] }), isLoading ? (_jsx("div", { className: "text-center py-12", children: _jsx("div", { className: "loading loading-spinner loading-lg" }) })) : (_jsxs(_Fragment, { children: [_jsx("div", { className: "grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-4", children: data?.items.map((role) => (_jsx("div", { className: "card bg-base-100 shadow-sm hover:shadow-lg transition-shadow", children: _jsxs("div", { className: "card-body p-6", children: [_jsxs("div", { className: "flex items-start justify-between mb-4", children: [_jsxs("div", { className: "flex items-center gap-3", children: [_jsx("div", { className: "p-2 bg-primary/10 rounded-lg", children: _jsx(Shield, { className: "w-5 h-5 text-primary" }) }), _jsxs("div", { children: [_jsx("h3", { className: "font-semibold text-lg", children: role.name }), role.isSystem && (_jsx("span", { className: "text-xs text-base-content/60", children: "H\u1EC7 th\u1ED1ng" }))] })] }), !role.isSystem && (_jsxs("div", { className: "flex gap-2", children: [_jsx("button", { onClick: () => handleEdit(role), className: "btn btn-ghost btn-sm btn-square", title: "Ch\u1EC9nh s\u1EEDa", children: _jsx(Edit, { className: "w-4 h-4" }) }), _jsx("button", { onClick: () => handleDelete(role), className: "btn btn-ghost btn-sm btn-square text-error", title: "X\u00F3a", children: _jsx(Trash2, { className: "w-4 h-4" }) })] }))] }), _jsx("p", { className: "text-sm text-base-content/60 mb-4", children: role.description || 'Không có mô tả' }), _jsxs("div", { className: "flex items-center justify-between pt-4 border-t border-base-300", children: [_jsxs("span", { className: "text-sm text-base-content/60", children: [role.permissionsCount, " quy\u1EC1n"] }), role.isSystem && (_jsx("button", { onClick: () => handleEdit(role), className: "link link-primary text-sm", children: "Xem chi ti\u1EBFt" }))] })] }) }, role.id))) }), data && data.totalPages > 1 && (_jsxs("div", { className: "flex justify-center gap-2 mt-6", children: [_jsx("button", { onClick: () => setCurrentPage((p) => Math.max(1, p - 1)), disabled: currentPage === 1, className: "btn btn-outline", children: "Tr\u01B0\u1EDBc" }), _jsxs("span", { className: "flex items-center px-4", children: ["Trang ", currentPage, " / ", data.totalPages] }), _jsx("button", { onClick: () => setCurrentPage((p) => Math.min(data.totalPages, p + 1)), disabled: currentPage === data.totalPages, className: "btn btn-outline", children: "Sau" })] })), data?.items.length === 0 && (_jsxs("div", { className: "text-center py-12", children: [_jsx(Shield, { className: "w-12 h-12 text-base-content/40 mx-auto mb-4" }), _jsx("p", { className: "text-base-content/60", children: "Kh\u00F4ng t\u00ECm th\u1EA5y vai tr\u00F2 n\u00E0o" })] }))] })), _jsx(RoleModal, { isOpen: isRoleModalOpen, onClose: handleRoleModalClose, onSuccess: handleRoleSuccess, role: selectedRole }), _jsx(ConfirmModal, { isOpen: deleteConfirmOpen, onClose: () => setDeleteConfirmOpen(false), onConfirm: confirmDelete, title: "X\u00E1c nh\u1EADn x\u00F3a vai tr\u00F2", message: `Bạn có chắc chắn muốn xóa vai trò "${roleToDelete?.name}"? Hành động này không thể hoàn tác.`, confirmText: "X\u00F3a", cancelText: "H\u1EE7y", type: "danger" })] }) }));
|
|
81
|
+
}
|
|
82
|
+
//# sourceMappingURL=RolesPage.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"RolesPage.js","sourceRoot":"","sources":["../../../src/client/pages/RolesPage.tsx"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"UnauthorizedPage.d.ts","sourceRoot":"","sources":["../../../src/client/pages/UnauthorizedPage.tsx"],"names":[],"mappings":"AAKA,MAAM,CAAC,OAAO,UAAU,gBAAgB,4CAwCvC"}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
'use client';
|
|
2
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
3
|
+
import Link from 'next/link';
|
|
4
|
+
import { useAdminConfig } from '../config/AdminConfigContext';
|
|
5
|
+
export default function UnauthorizedPage() {
|
|
6
|
+
const { resolvedRoutes } = useAdminConfig();
|
|
7
|
+
return (_jsx("div", { className: "min-h-screen flex items-center justify-center bg-gray-50", children: _jsxs("div", { className: "max-w-md w-full space-y-8", children: [_jsxs("div", { className: "text-center", children: [_jsx("div", { className: "mx-auto h-12 w-12 text-red-500", children: _jsx("svg", { fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", xmlns: "http://www.w3.org/2000/svg", children: _jsx("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M12 9v2m0 4h.01m-6.938 4h13.856c1.54 0 2.502-1.667 1.732-2.5L13.732 4c-.77-.833-1.964-.833-2.732 0L4.082 16.5c-.77.833.192 2.5 1.732 2.5z" }) }) }), _jsx("h2", { className: "mt-6 text-3xl font-extrabold text-gray-900", children: "Kh\u00F4ng c\u00F3 quy\u1EC1n truy c\u1EADp" }), _jsx("p", { className: "mt-2 text-sm text-gray-600", children: "B\u1EA1n kh\u00F4ng c\u00F3 quy\u1EC1n truy c\u1EADp trang n\u00E0y. Vui l\u00F2ng li\u00EAn h\u1EC7 qu\u1EA3n tr\u1ECB vi\u00EAn n\u1EBFu b\u1EA1n c\u1EA7n quy\u1EC1n truy c\u1EADp." })] }), _jsx("div", { className: "mt-8 space-y-4", children: _jsx(Link, { href: resolvedRoutes.DASHBOARD, className: "group relative w-full flex justify-center py-2 px-4 border border-transparent text-sm font-medium rounded-md text-white bg-indigo-600 hover:bg-indigo-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-indigo-500", children: "Quay v\u1EC1 Dashboard" }) })] }) }));
|
|
8
|
+
}
|
|
9
|
+
//# sourceMappingURL=UnauthorizedPage.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"UnauthorizedPage.js","sourceRoot":"","sources":["../../../src/client/pages/UnauthorizedPage.tsx"],"names":[],"mappings":"AAAA,YAAY,CAAA;;AAEZ,OAAO,IAAI,MAAM,WAAW,CAAA;AAC5B,OAAO,EAAE,cAAc,EAAE,MAAM,8BAA8B,CAAA;AAE7D,MAAM,CAAC,OAAO,UAAU,gBAAgB;IACtC,MAAM,EAAE,cAAc,EAAE,GAAG,cAAc,EAAE,CAAA;IAE3C,OAAO,CACL,cAAK,SAAS,EAAC,0DAA0D,YACvE,eAAK,SAAS,EAAC,2BAA2B,aACxC,eAAK,SAAS,EAAC,aAAa,aAC1B,cAAK,SAAS,EAAC,gCAAgC,YAC7C,cACE,IAAI,EAAC,MAAM,EACX,MAAM,EAAC,cAAc,EACrB,OAAO,EAAC,WAAW,EACnB,KAAK,EAAC,4BAA4B,YAElC,eACE,aAAa,EAAC,OAAO,EACrB,cAAc,EAAC,OAAO,EACtB,WAAW,EAAE,CAAC,EACd,CAAC,EAAC,2IAA2I,GAC7I,GACE,GACF,EACN,aAAI,SAAS,EAAC,4CAA4C,4DAErD,EACL,YAAG,SAAS,EAAC,4BAA4B,uMAErC,IACA,EACN,cAAK,SAAS,EAAC,gBAAgB,YAC7B,KAAC,IAAI,IACH,IAAI,EAAE,cAAc,CAAC,SAAS,EAC9B,SAAS,EAAC,qOAAqO,uCAG1O,GACH,IACF,GACF,CACP,CAAA;AACH,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"UserDetailPage.d.ts","sourceRoot":"","sources":["../../../src/client/pages/UserDetailPage.tsx"],"names":[],"mappings":"AAmBA,UAAU,mBAAmB;IAC3B,MAAM,EAAE,MAAM,CAAA;CACf;AAmBD,MAAM,CAAC,OAAO,UAAU,cAAc,CAAC,EAAE,MAAM,EAAE,EAAE,mBAAmB,2CA+UrE"}
|