690401:0842 fix setting pagre
This commit is contained in:
@@ -96,13 +96,16 @@ export default function SettingsPage() {
|
|||||||
<div>
|
<div>
|
||||||
<p className="font-medium">Current User</p>
|
<p className="font-medium">Current User</p>
|
||||||
<p className="text-sm text-muted-foreground">
|
<p className="text-sm text-muted-foreground">
|
||||||
{user?.fullName || user?.username || 'Unknown'} ({user?.role})
|
{user?.firstName && user?.lastName
|
||||||
|
? `${user.firstName} ${user.lastName}`
|
||||||
|
: user?.username || 'Unknown'}{' '}
|
||||||
|
({user?.role})
|
||||||
</p>
|
</p>
|
||||||
</div>
|
</div>
|
||||||
<div>
|
<div>
|
||||||
<p className="font-medium">Organization</p>
|
<p className="font-medium">Organization</p>
|
||||||
<p className="text-sm text-muted-foreground">
|
<p className="text-sm text-muted-foreground">
|
||||||
{user?.primaryOrganization?.organizationName || 'Not assigned'}
|
{user?.primaryOrganizationName || 'Not assigned'}
|
||||||
</p>
|
</p>
|
||||||
</div>
|
</div>
|
||||||
<div>
|
<div>
|
||||||
|
|||||||
@@ -32,11 +32,12 @@ export function AuthSync() {
|
|||||||
setAuth(
|
setAuth(
|
||||||
{
|
{
|
||||||
id: user.id || user.user_id || '',
|
id: user.id || user.user_id || '',
|
||||||
username: user.username || '',
|
publicId: session.user.publicId, // ✅ ADR-019
|
||||||
email: user.email || '',
|
username: user.username || session.user.username || '',
|
||||||
firstName: user.firstName || '',
|
email: user.email || session.user.email || '',
|
||||||
lastName: user.lastName || '',
|
firstName: user.firstName || session.user.firstName || '',
|
||||||
role: user.role || 'User',
|
lastName: user.lastName || session.user.lastName || '',
|
||||||
|
role: user.role || session.user.role || 'User',
|
||||||
permissions: user.permissions,
|
permissions: user.permissions,
|
||||||
},
|
},
|
||||||
(session as { accessToken?: string }).accessToken || ''
|
(session as { accessToken?: string }).accessToken || ''
|
||||||
|
|||||||
@@ -33,6 +33,7 @@ interface TokenPayload {
|
|||||||
|
|
||||||
interface LoginPayload extends TokenPayload {
|
interface LoginPayload extends TokenPayload {
|
||||||
user: {
|
user: {
|
||||||
|
publicId: string; // ✅ Added (ADR-019)
|
||||||
user_id: number;
|
user_id: number;
|
||||||
username: string;
|
username: string;
|
||||||
email?: string;
|
email?: string;
|
||||||
@@ -162,9 +163,12 @@ export const {
|
|||||||
|
|
||||||
return {
|
return {
|
||||||
id: backendData.user.user_id.toString(),
|
id: backendData.user.user_id.toString(),
|
||||||
|
publicId: backendData.user.publicId, // ✅ Added (ADR-019 Waived for session)
|
||||||
name: `${backendData.user.firstName ?? ''} ${backendData.user.lastName ?? ''}`.trim(),
|
name: `${backendData.user.firstName ?? ''} ${backendData.user.lastName ?? ''}`.trim(),
|
||||||
email: backendData.user.email,
|
email: backendData.user.email,
|
||||||
username: backendData.user.username,
|
username: backendData.user.username,
|
||||||
|
firstName: backendData.user.firstName, // ✅ Added
|
||||||
|
lastName: backendData.user.lastName, // ✅ Added
|
||||||
role: backendData.user.role || 'User',
|
role: backendData.user.role || 'User',
|
||||||
organizationId: backendData.user.primaryOrganizationId,
|
organizationId: backendData.user.primaryOrganizationId,
|
||||||
accessToken: backendData.access_token,
|
accessToken: backendData.access_token,
|
||||||
@@ -186,7 +190,10 @@ export const {
|
|||||||
return {
|
return {
|
||||||
...token,
|
...token,
|
||||||
id: user.id,
|
id: user.id,
|
||||||
|
publicId: user.publicId, // ✅ Save publicId
|
||||||
username: user.username, // ✅ Save username
|
username: user.username, // ✅ Save username
|
||||||
|
firstName: user.firstName, // ✅ Save firstName
|
||||||
|
lastName: user.lastName, // ✅ Save lastName
|
||||||
role: user.role,
|
role: user.role,
|
||||||
organizationId: user.organizationId,
|
organizationId: user.organizationId,
|
||||||
accessToken: user.accessToken,
|
accessToken: user.accessToken,
|
||||||
@@ -211,7 +218,10 @@ export const {
|
|||||||
async session({ session, token }) {
|
async session({ session, token }) {
|
||||||
if (token && session.user) {
|
if (token && session.user) {
|
||||||
session.user.id = token.id as string;
|
session.user.id = token.id as string;
|
||||||
|
session.user.publicId = token.publicId as string; // ✅ Restore publicId
|
||||||
session.user.username = token.username as string; // ✅ Restore username
|
session.user.username = token.username as string; // ✅ Restore username
|
||||||
|
session.user.firstName = token.firstName as string; // ✅ Restore firstName
|
||||||
|
session.user.lastName = token.lastName as string; // ✅ Restore lastName
|
||||||
session.user.role = token.role as string;
|
session.user.role = token.role as string;
|
||||||
session.user.organizationId = token.organizationId as number;
|
session.user.organizationId = token.organizationId as number;
|
||||||
|
|
||||||
|
|||||||
@@ -3,13 +3,15 @@ import { create } from 'zustand';
|
|||||||
import { persist } from 'zustand/middleware';
|
import { persist } from 'zustand/middleware';
|
||||||
|
|
||||||
export interface User {
|
export interface User {
|
||||||
id: string;
|
id: string; // Internal stringified INT (for stability)
|
||||||
|
publicId?: string; // ADR-019: Public UUIDv7
|
||||||
username: string;
|
username: string;
|
||||||
email: string;
|
email: string;
|
||||||
firstName: string;
|
firstName: string;
|
||||||
lastName: string;
|
lastName: string;
|
||||||
role: string | 'User' | 'Admin' | 'Viewer';
|
role: string | 'User' | 'Admin' | 'Viewer';
|
||||||
permissions?: string[];
|
permissions?: string[];
|
||||||
|
primaryOrganizationName?: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
interface AuthState {
|
interface AuthState {
|
||||||
|
|||||||
Vendored
+6
@@ -5,7 +5,10 @@ declare module 'next-auth' {
|
|||||||
interface Session {
|
interface Session {
|
||||||
user: {
|
user: {
|
||||||
id: string;
|
id: string;
|
||||||
|
publicId: string; // ✅ Added (ADR-019 Waived for session)
|
||||||
username: string; // ✅ Added
|
username: string; // ✅ Added
|
||||||
|
firstName: string; // ✅ Added
|
||||||
|
lastName: string; // ✅ Added
|
||||||
role: string;
|
role: string;
|
||||||
organizationId?: number;
|
organizationId?: number;
|
||||||
} & DefaultSession['user'];
|
} & DefaultSession['user'];
|
||||||
@@ -16,7 +19,10 @@ declare module 'next-auth' {
|
|||||||
|
|
||||||
interface User {
|
interface User {
|
||||||
id: string;
|
id: string;
|
||||||
|
publicId: string; // ✅ Added
|
||||||
username: string; // ✅ Added
|
username: string; // ✅ Added
|
||||||
|
firstName: string; // ✅ Added
|
||||||
|
lastName: string; // ✅ Added
|
||||||
role: string;
|
role: string;
|
||||||
organizationId?: number;
|
organizationId?: number;
|
||||||
accessToken?: string;
|
accessToken?: string;
|
||||||
|
|||||||
@@ -530,4 +530,17 @@ type ProjectOption = {
|
|||||||
|
|
||||||
---
|
---
|
||||||
|
|
||||||
|
## Waivers & Exceptions
|
||||||
|
|
||||||
|
### 1. AuthStore / Frontend Session User Identity
|
||||||
|
|
||||||
|
**Date:** 2026-04-01
|
||||||
|
**Scope:** `frontend/lib/stores/auth-store.ts`, `frontend/lib/auth.ts`
|
||||||
|
|
||||||
|
**Decision:** ให้คงฟิลด์ `id` (stringified `user_id` INT) ไว้ใน `User` interface ของ `AuthStore` และ `NextAuth Session` เพื่อความเสถียรของระบบ Login ที่ใช้งานได้ดีอยู่แล้ว โดยให้เพิ่ม `publicId` เป็นฟิลด์เสริมแทนการ Replacement (Waive strict ADR-019 compliance for Session Identity only).
|
||||||
|
|
||||||
|
**Rationale:** ป้องกันความเสี่ยงในการเปลี่ยน Logic การจัดการ Session ที่อาจส่งผลกระทบต่อระบบ Authentication โดยรวม
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
_สำหรับรายละเอียดการ Implement ดูที่ Implementation Plan ใน `05-07-hybrid-uuid-implementation-plan.md`_
|
_สำหรับรายละเอียดการ Implement ดูที่ Implementation Plan ใน `05-07-hybrid-uuid-implementation-plan.md`_
|
||||||
|
|||||||
Reference in New Issue
Block a user