app/src/types/navigation.ts
2025-11-14 14:47:26 +00:00

343 lines
9.4 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

import { CalendarNode, WorkerNode } from '../contexts/NeoUserContext';
import { logger } from '../debugConfig';
// Main Context Types
export type MainContext = 'profile' | 'institute';
// Profile Context Types
export type ProfileContext = 'profile' | 'calendar' | 'teaching';
// Extended Context Types
export type UserExtendedContext = 'overview' | 'settings' | 'history' | 'journal' | 'planner';
export type CalendarExtendedContext = 'overview' | 'day' | 'week' | 'month' | 'year';
export type TeacherExtendedContext =
| 'overview'
| 'timetable'
| 'classes'
| 'lessons'
| 'journal'
| 'planner';
export type SchoolExtendedContext = 'overview' | 'departments' | 'staff';
export type DepartmentExtendedContext = 'overview' | 'teachers' | 'subjects';
export type ClassExtendedContext = 'overview' | 'students' | 'timetable';
// Combined Extended Context Type
export type ExtendedContext =
| UserExtendedContext
| CalendarExtendedContext
| TeacherExtendedContext
| SchoolExtendedContext
| DepartmentExtendedContext
| ClassExtendedContext;
// View Definition
export interface ViewDefinition {
id: ExtendedContext;
icon: string;
label: string;
description: string;
}
// Institute Context Types
export type InstituteContext = 'school' | 'department' | 'class';
// View Context Types
export type ViewContext =
| 'overview'
| 'settings'
| 'history'
| 'journal'
| 'planner'
| 'day'
| 'week'
| 'month'
| 'year'
| 'timetable'
| 'classes'
| 'lessons'
| 'departments'
| 'staff'
| 'teachers'
| 'subjects'
| 'students';
// Combined Context Type
export type BaseContext = ProfileContext | InstituteContext;
// Combined Node Context Type
export type NodeContext = BaseContext | ExtendedContext;
// Navigation History
export interface NavigationHistory {
nodes: NavigationNode[];
currentIndex: number;
}
// Helper function to get current node from history
export const getCurrentHistoryNode = (history: NavigationHistory): NavigationNode | null => {
const node = history.currentIndex === -1 || !history.nodes.length ? null : history.nodes[history.currentIndex];
logger.debug('history-management', '📍 Getting current history node', {
currentIndex: history.currentIndex,
totalNodes: history.nodes.length,
node
});
return node;
};
// Helper function to add node to history
export const addToHistory = (
history: NavigationHistory,
node: NavigationNode
): NavigationHistory => {
logger.debug('history-management', ' Adding node to history', {
currentIndex: history.currentIndex,
newNode: node,
existingNodes: history.nodes.length
});
const newNodes = [...history.nodes.slice(0, history.currentIndex + 1), node];
const newHistory = {
nodes: newNodes,
currentIndex: newNodes.length - 1
};
logger.debug('history-management', '✅ History updated', {
previousState: history,
newState: newHistory
});
return newHistory;
};
// Helper function to navigate history
export const navigateHistory = (
history: NavigationHistory,
index: number
): NavigationHistory => {
logger.debug('history-management', '🔄 Navigating history', {
currentIndex: history.currentIndex,
targetIndex: index,
totalNodes: history.nodes.length
});
if (index < 0 || index >= history.nodes.length) {
logger.warn('history-management', '⚠️ Invalid history navigation index', {
requestedIndex: index,
historyLength: history.nodes.length
});
return history;
}
const newHistory = {
nodes: history.nodes,
currentIndex: index
};
logger.debug('history-management', '✅ History navigation complete', {
from: history.currentIndex,
to: index,
node: history.nodes[index]
});
return newHistory;
};
// Context State Interface
export interface NavigationContextState {
main: MainContext;
base: BaseContext;
node: NavigationNode | null;
history: NavigationHistory;
}
// Type Guards
export const isProfileContext = (context: BaseContext): context is ProfileContext => {
return ['profile', 'calendar', 'teaching'].includes(context);
};
export const isInstituteContext = (context: BaseContext): context is InstituteContext => {
return ['school', 'department', 'class'].includes(context);
};
// Database selector
export const getContextDatabase = (context: NavigationContextState, userDbName: string | null, workerDbName: string | null): string => {
logger.debug('navigation-context', '🔄 Getting context database', {
mainContext: context.main,
baseContext: context.base,
userDbName,
workerDbName
});
if (context.main === 'profile') {
if (!userDbName) {
logger.error('navigation-context', '❌ Missing user database name for profile context');
throw new Error('User database name is required for profile context');
}
logger.debug('navigation-context', '✅ Using user database', { dbName: userDbName });
return userDbName;
} else {
if (!workerDbName) {
logger.error('navigation-context', '❌ Missing worker database name for institute context');
throw new Error('Worker database name is required for institute context');
}
logger.debug('navigation-context', '✅ Using worker database', { dbName: workerDbName });
return workerDbName;
}
};
// Context Definition Types
export interface ContextDefinition {
id: BaseContext;
icon: string;
label: string;
description: string;
defaultNodeId: string;
views: ViewDefinition[];
}
// Navigation Node Types
export interface NavigationNode {
id: string;
node_storage_path: string;
label: string;
type: string;
context?: NavigationContextState;
data?: {
uuid_string: string;
node_storage_path: string;
title?: string;
name?: string;
[key: string]: unknown;
};
}
// Navigation State Interface
export interface NavigationState {
context: NavigationContextState;
isLoading: boolean;
error: string | null;
}
// Add UnifiedContextSwitch interface
export interface UnifiedContextSwitch {
main?: MainContext;
base?: BaseContext;
extended?: ExtendedContext;
skipBaseContextLoad?: boolean;
}
// Navigation Actions Interface
export interface NavigationActions {
// Unified Context Switch
switchContext: (contextSwitch: UnifiedContextSwitch, userDbName: string | null, workerDbName: string | null) => Promise<void>;
// Context Navigation
setMainContext: (context: MainContext, userDbName: string | null, workerDbName: string | null) => Promise<void>;
setBaseContext: (context: BaseContext, userDbName: string | null, workerDbName: string | null) => Promise<void>;
setExtendedContext: (context: ExtendedContext, userDbName: string | null, workerDbName: string | null) => Promise<void>;
// Node Navigation
navigate: (nodeId: string, dbName: string) => Promise<void>;
navigateToNode: (node: NavigationNode, userDbName: string | null, workerDbName: string | null) => Promise<void>;
// History Navigation
goBack: () => void;
goForward: () => void;
// Utility Methods
refreshNavigationState: (userDbName: string | null, workerDbName: string | null) => Promise<void>;
}
export type NavigationStore = NavigationState & NavigationActions;
// Context Props Interfaces
export interface CalendarContextProps {
navigateToDay: (id: string) => Promise<void>;
navigateToWeek: (id: string) => Promise<void>;
navigateToMonth: (id: string) => Promise<void>;
navigateToYear: (id: string) => Promise<void>;
currentCalendarNode: CalendarNode | null;
}
export interface WorkerContextProps {
navigateToTimetable: (id: string) => Promise<void>;
navigateToClass: (id: string) => Promise<void>;
navigateToLesson: (id: string) => Promise<void>;
navigateToJournal: (id: string) => Promise<void>;
navigateToPlanner: (id: string) => Promise<void>;
currentWorkerNode: WorkerNode | null;
}
export interface StaticNavigationNode extends NavigationNode {
isStatic: true;
order: number;
section: string;
}
// Calendar Structure Types
export interface CalendarDay {
id: string;
date: string;
title: string;
}
export interface CalendarWeek {
id: string;
title: string;
days: { id: string }[];
startDate: string;
endDate: string;
}
export interface CalendarMonth {
id: string;
title: string;
days: { id: string }[];
weeks: { id: string }[];
year: string;
month: string;
}
export interface CalendarYear {
id: string;
title: string;
months: { id: string }[];
year: string;
}
export interface CalendarStructure {
currentDay: string;
days: Record<string, CalendarDay>;
weeks: Record<string, CalendarWeek>;
months: Record<string, CalendarMonth>;
years: CalendarYear[];
}
// Worker Structure Types
export interface TimetableEntry {
id: string;
title: string;
type: string;
startTime: string;
endTime: string;
}
export interface ClassEntry {
id: string;
title: string;
type: string;
}
export interface LessonEntry {
id: string;
title: string;
type: string;
}
export interface WorkerStructure {
timetables: Record<string, TimetableEntry[]>;
classes: Record<string, ClassEntry[]>;
lessons: Record<string, LessonEntry[]>;
journals: Record<string, { id: string; title: string }[]>;
planners: Record<string, { id: string; title: string }[]>;
}