Files
bedolaga-cabinet/src/pages/ConnectionQR.tsx
c0mrade 8ce4b1a24a refactor: move ConnectionQR into standard Layout with proper navigation
- Wrap /connection/qr route in ProtectedRoute with Layout
- Remove fullscreen overlay and custom close button
- Add AdminBackButton with replace prop to avoid history cycles
- Use replace navigation from Connection to QR page
- Add replace prop support to AdminBackButton component
2026-03-07 23:25:33 +03:00

77 lines
2.3 KiB
TypeScript

import { useEffect } from 'react';
import { useLocation, useNavigate } from 'react-router';
import { useTranslation } from 'react-i18next';
import { QRCodeSVG } from 'qrcode.react';
import { useBranding } from '../hooks/useBranding';
import { AdminBackButton } from '@/components/admin';
interface ConnectionQRState {
url: string;
hideLink: boolean;
}
function isValidState(state: unknown): state is ConnectionQRState {
if (!state || typeof state !== 'object') return false;
const s = state as Record<string, unknown>;
return typeof s.url === 'string' && s.url.length > 0 && typeof s.hideLink === 'boolean';
}
export default function ConnectionQR() {
const { t } = useTranslation();
const navigate = useNavigate();
const location = useLocation();
const { appName } = useBranding();
const state = location.state as unknown;
const validState = isValidState(state) ? state : null;
useEffect(() => {
if (!validState) {
navigate('/connection', { replace: true });
}
}, [validState, navigate]);
if (!validState) {
return null;
}
return (
<div className="animate-fade-in">
<div className="mb-6 flex items-center gap-3">
<AdminBackButton to="/connection" replace />
<h1 className="text-2xl font-bold text-dark-100">{t('subscription.connection.qrTitle')}</h1>
</div>
<div className="flex flex-col items-center">
<div className="flex w-full max-w-sm flex-col items-center px-6">
{appName && (
<p className="mb-3 text-sm font-medium uppercase tracking-wider text-dark-400">
{appName}
</p>
)}
<p className="mb-8 text-center text-sm text-dark-400">
{t('subscription.connection.qrScanHint')}
</p>
<div className="rounded-3xl bg-white p-6">
<QRCodeSVG
value={validState.url}
size={280}
level="M"
includeMargin={false}
className="h-[280px] w-[280px] sm:h-[360px] sm:w-[360px]"
/>
</div>
{!validState.hideLink && (
<p className="mt-6 max-w-full truncate text-center font-mono text-xs text-dark-500">
{validState.url}
</p>
)}
</div>
</div>
</div>
);
}