feat(reui): update ReUI components and documentation
Build and Push Auth Portal Docker Image / build-and-push (push) Successful in 2m30s
Build and Push Auth Portal Docker Image / create-release (push) Skipped

- Added new OIDC configuration options in `.env.example`.
- Expanded documentation in `AGENTS.md` to include OIDC endpoints and admin UI.
- Updated ReUI skill version and component count from 17 to 20 across various documentation files.
- Enhanced `README.md` and other related files to reflect the new component structure and usage guidelines.

Co-authored-by: Cursor <[email protected]>
This commit is contained in:
Denozordec
2026-08-11 16:58:47 +07:00
co-authored by Cursor
parent cc38bf06f8
commit 0b6fa65b08
61 changed files with 2387 additions and 103 deletions
+13 -1
View File
@@ -3,6 +3,7 @@ import { useQuery } from '@tanstack/react-query'
import {
AppWindowIcon,
HistoryIcon,
KeyRoundIcon,
LayoutGridIcon,
LogInIcon,
UsersIcon,
@@ -68,7 +69,8 @@ export function AppSidebar() {
isActive(pathname, '/admin', false) &&
!pathname.startsWith('/admin/apps') &&
!pathname.startsWith('/admin/audit') &&
!pathname.startsWith('/admin/logins')
!pathname.startsWith('/admin/logins') &&
!pathname.startsWith('/admin/oidc')
}
render={<Link to="/admin" />}
>
@@ -106,6 +108,16 @@ export function AppSidebar() {
<span>Ссылки приложений</span>
</SidebarMenuButton>
</SidebarMenuItem>
<SidebarMenuItem>
<SidebarMenuButton
tooltip="OIDC"
isActive={isActive(pathname, '/admin/oidc', false)}
render={<Link to="/admin/oidc" />}
>
<KeyRoundIcon className="size-4" />
<span>OIDC-клиенты</span>
</SidebarMenuButton>
</SidebarMenuItem>
</SidebarMenu>
</SidebarGroupContent>
</SidebarGroup>
+1 -1
View File
@@ -91,7 +91,7 @@ export function AppSwitcher() {
<DropdownMenuItem
key={app.id}
onClick={() => {
void ssoOpenApp(app.url).catch(() => {
void ssoOpenApp(app.url, app.authMode ?? 'jwt').catch(() => {
window.location.href = app.url.replace(/\/$/, '')
})
}}
@@ -6,6 +6,7 @@ import {
ServerIcon,
NetworkIcon,
ShieldIcon,
GlobeIcon,
} from 'lucide-react'
import { APPS, type AppId } from '@authportal/shared'
import { Button } from '@authportal/ui/components/button'
@@ -26,6 +27,7 @@ const APP_ICONS: Record<
vps: ServerIcon,
bgp: NetworkIcon,
fw: ShieldIcon,
dns: GlobeIcon,
}
export function AppsMenu() {
@@ -16,6 +16,9 @@ function breadcrumbs(pathname: string) {
if (pathname.startsWith('/admin/apps')) {
return [{ label: 'Ссылки приложений', href: '/admin/apps' }]
}
if (pathname.startsWith('/admin/oidc')) {
return [{ label: 'OIDC-клиенты', href: '/admin/oidc' }]
}
if (pathname.startsWith('/admin/logins')) {
return [{ label: 'Журнал входов', href: '/admin/logins' }]
}
@@ -2,7 +2,7 @@ import { useState, type FormEvent } from 'react'
import { useNavigate, useSearch } from '@tanstack/react-router'
import { useQueryClient } from '@tanstack/react-query'
import { EyeIcon, EyeOffIcon } from 'lucide-react'
import { buildSsoRedirectUrl, isReturnToAllowed } from '@authportal/shared'
import { buildSsoRedirectUrl, isPortalOidcAuthorizeUrl, isReturnToAllowed } from '@authportal/shared'
import { Button } from '@authportal/ui/components/button'
import { Field, FieldGroup, FieldLabel } from '@authportal/ui/components/field'
import { Input } from '@authportal/ui/components/input'
@@ -17,7 +17,7 @@ import {
AlertDescription,
AlertTitle,
} from '@/components/reui/alert'
import { ensureReturnToAllowlist, setToken } from '@/lib/auth'
import { ensureAuthConfig, setToken } from '@/lib/auth'
import { ApiError } from '@/lib/api-client'
import { login, meQueryKey } from '@/queries/auth'
import { AuthLogo } from '@/components/blocks/auth-18/components/auth-logo'
@@ -43,8 +43,12 @@ export function PortalLoginForm() {
setToken(res.access_token)
queryClient.setQueryData(meQueryKey, res.user)
const allowlist = await ensureReturnToAllowlist()
const { returnToAllowlist: allowlist, issuer } = await ensureAuthConfig()
if (returnTo && isReturnToAllowed(returnTo, allowlist)) {
if (isPortalOidcAuthorizeUrl(returnTo, issuer)) {
window.location.href = returnTo
return
}
window.location.href = buildSsoRedirectUrl(
returnTo,
res.access_token,
@@ -42,6 +42,7 @@ export const SOURCE_APP_OPTIONS: {
{ value: 'cfdm', label: 'CFDM' },
{ value: 'bgp', label: 'EvoBGP' },
{ value: 'fw', label: 'EvoFirewall' },
{ value: 'dns', label: 'Technitium DNS' },
]
export const severityVariant: Record<AuditSeverity, BadgeProps['variant']> = {