418 lines
16 KiB
TypeScript
418 lines
16 KiB
TypeScript
/**
|
|
* MENU REGISTRY — sursa unica de adevar pentru Main Navigator (14 sectiuni).
|
|
*
|
|
* Cerinta din spec: meniul e configurabil prin date, nu hardcodat in componente.
|
|
* Fiecare element are route, icon, permissions, featureFlag, workspaceTypes,
|
|
* releaseStage si (la sectiuni) children. Sidebar-ul si ruta catch-all pentru
|
|
* sectiunile neconstruite citesc amandoua de aici.
|
|
*
|
|
* status vs releaseStage sunt lucruri diferite si nu se confunda:
|
|
* releaseStage = CAND e planificat sa existe (mvp / a3 / a4)
|
|
* status = daca exista ACUM in cod ('ready') sau nu ('planned')
|
|
*/
|
|
|
|
/** Rolurile care exista efectiv in baza (memberships.role). Rolurile din blueprint
|
|
* (accountant, consultant, data_analyst, family_member...) nu sunt inca modelate. */
|
|
export type Role = 'owner' | 'admin' | 'member';
|
|
|
|
export type ReleaseStage = 'mvp' | 'a3' | 'a4';
|
|
export type NavStatus = 'ready' | 'planned';
|
|
|
|
/** Tipuri de workspace din spec (Workspace Switcher). Momentan exista doar 'business'
|
|
* ca tenant; restul sunt pregatite in contract, nu inca in date. */
|
|
export type WorkspaceType = 'personal' | 'family' | 'business' | 'community';
|
|
|
|
const ALL_WORKSPACES: WorkspaceType[] = ['personal', 'family', 'business', 'community'];
|
|
|
|
export interface NavItem {
|
|
label: string;
|
|
route: string;
|
|
status: NavStatus;
|
|
releaseStage: ReleaseStage;
|
|
/** undefined = vizibil pentru toate rolurile */
|
|
permissions?: Role[];
|
|
featureFlag?: string;
|
|
workspaceTypes?: WorkspaceType[];
|
|
/** Ce lipseste concret ca sa devina 'ready'. Afisat pe pagina planned. */
|
|
missing?: string;
|
|
}
|
|
|
|
export interface NavSection {
|
|
/** Numar de ordine din spec (01..14), pastrat ca sa ramana urmaribil. */
|
|
order: string;
|
|
label: string;
|
|
icon: IconName;
|
|
releaseStage: ReleaseStage;
|
|
permissions?: Role[];
|
|
featureFlag?: string;
|
|
workspaceTypes?: WorkspaceType[];
|
|
children: NavItem[];
|
|
}
|
|
|
|
export type IconName =
|
|
| 'command'
|
|
| 'life'
|
|
| 'business'
|
|
| 'documents'
|
|
| 'intelligence'
|
|
| 'decisions'
|
|
| 'relationships'
|
|
| 'trust'
|
|
| 'ai'
|
|
| 'reports'
|
|
| 'data'
|
|
| 'integrations'
|
|
| 'privacy'
|
|
| 'settings';
|
|
|
|
const B = '/dashboard';
|
|
|
|
/** Prescurtare: majoritatea itemilor sunt planned pe toate workspace-urile. */
|
|
function planned(
|
|
label: string,
|
|
route: string,
|
|
releaseStage: ReleaseStage,
|
|
missing: string,
|
|
extra: Partial<NavItem> = {},
|
|
): NavItem {
|
|
return { label, route, status: 'planned', releaseStage, missing, ...extra };
|
|
}
|
|
|
|
function ready(label: string, route: string, extra: Partial<NavItem> = {}): NavItem {
|
|
return { label, route, status: 'ready', releaseStage: 'mvp', ...extra };
|
|
}
|
|
|
|
export const NAV_SECTIONS: NavSection[] = [
|
|
{
|
|
order: '01',
|
|
label: 'Command Center',
|
|
icon: 'command',
|
|
releaseStage: 'mvp',
|
|
workspaceTypes: ALL_WORKSPACES,
|
|
children: [
|
|
ready('Executive Overview', B),
|
|
ready('Daily Briefing', `${B}/briefing`),
|
|
ready('Priorities', `${B}/priorities`),
|
|
ready('Alerts & Deadlines', `${B}/alerts`),
|
|
planned(
|
|
'Approval Center',
|
|
`${B}/approvals`,
|
|
'mvp',
|
|
'Coada de aprobare pentru actiuni materiale (blueprint 14.3). AI Gateway blocheaza deja clasele material/high_risk pana exista aceasta coada + idempotency.',
|
|
),
|
|
ready('Activity Timeline', `${B}/activity`),
|
|
planned(
|
|
'Daily / Weekly Review',
|
|
`${B}/review`,
|
|
'mvp',
|
|
'Retrospectiva zilnica/saptamanala peste taskuri, decizii si modificari.',
|
|
),
|
|
],
|
|
},
|
|
{
|
|
order: '02',
|
|
label: 'Life OS',
|
|
icon: 'life',
|
|
releaseStage: 'a3',
|
|
workspaceTypes: ['personal', 'family'],
|
|
children: [
|
|
ready('Personal Dashboard', `${B}/life`),
|
|
ready('Goals', `${B}/goals`, { releaseStage: 'a3' }),
|
|
ready('Calendar & Time', `${B}/calendar`),
|
|
ready('Tasks & Routines', `${B}/routines`),
|
|
ready('Energy & Wellbeing', `${B}/energy`),
|
|
ready('Education & Development', `${B}/education`),
|
|
ready('Personal KPI', `${B}/personal-kpi`),
|
|
ready('Life Analytics', `${B}/life-analytics`),
|
|
planned('Family OS', `${B}/family`, 'a3', 'Rol Family Member + politici pentru minori + consimtamant per membru.'),
|
|
],
|
|
},
|
|
{
|
|
order: '03',
|
|
label: 'Business OS',
|
|
icon: 'business',
|
|
releaseStage: 'mvp',
|
|
workspaceTypes: ['business'],
|
|
children: [
|
|
ready('Business Overview', `${B}/business`),
|
|
ready('Organizations', `${B}/organizations`),
|
|
ready('CRM & Contacts', `${B}/crm`),
|
|
ready('Sales Pipeline', `${B}/pipeline`),
|
|
ready('Projects', `${B}/projects`),
|
|
ready('Tasks & Operations', `${B}/tasks`),
|
|
ready('Finance', `${B}/finance`),
|
|
ready('Transactions', `${B}/transactions`),
|
|
ready('Cash Flow', `${B}/cash-flow`),
|
|
ready('Contracts', `${B}/contracts`),
|
|
ready('Deadlines & Obligations', `${B}/obligations`),
|
|
ready('Risks', `${B}/risks`),
|
|
ready('Accountant Pack', `${B}/accountant-pack`),
|
|
planned('ERP', `${B}/erp`, 'mvp', 'ERPNext ruleaza pe server. CEO OS nu scrie direct in baza ERP: doar prin adapter/API.'),
|
|
],
|
|
},
|
|
{
|
|
order: '04',
|
|
label: 'Documents & Evidence',
|
|
icon: 'documents',
|
|
releaseStage: 'mvp',
|
|
workspaceTypes: ALL_WORKSPACES,
|
|
children: [
|
|
planned('Document Inbox', `${B}/documents/inbox`, 'mvp', 'Paperless-ngx ruleaza pe server dar nu e conectat la ceo-api. Necesita adapter + webhook semnat.'),
|
|
ready('Document Library', `${B}/documents`),
|
|
ready('OCR Review', `${B}/documents/ocr`),
|
|
ready('Evidence Center', `${B}/evidence`),
|
|
ready('Expirations', `${B}/expirations`),
|
|
ready('Document Templates', `${B}/documents/templates`),
|
|
ready('Shared Documents', `${B}/documents/shared`),
|
|
ready('Archive', `${B}/documents/archive`),
|
|
],
|
|
},
|
|
{
|
|
order: '05',
|
|
label: 'Intelligence',
|
|
icon: 'intelligence',
|
|
releaseStage: 'mvp',
|
|
workspaceTypes: ALL_WORKSPACES,
|
|
children: [
|
|
ready('Intelligence Overview', `${B}/intelligence`),
|
|
ready('Global Search', `${B}/search`),
|
|
ready('Company Intelligence', `${B}/companies`),
|
|
ready('People Intelligence', `${B}/intelligence/people`),
|
|
ready('Market Intelligence', `${B}/market`),
|
|
ready('Saved Segments', `${B}/segments`),
|
|
ready('Research Briefs', `${B}/research`),
|
|
ready('Legislation Search', `${B}/legislation`),
|
|
ready('Insights', `${B}/intelligence/insights`),
|
|
ready('Trends & Patterns', `${B}/trends`),
|
|
ready('Anomalies', `${B}/anomalies`),
|
|
ready('Memory & Knowledge', `${B}/memory`),
|
|
ready('Digital Twin', `${B}/digital-twin`),
|
|
ready('Performance Coach', `${B}/coach`),
|
|
],
|
|
},
|
|
{
|
|
order: '06',
|
|
label: 'Decisions & Opportunities',
|
|
icon: 'decisions',
|
|
releaseStage: 'mvp',
|
|
workspaceTypes: ALL_WORKSPACES,
|
|
children: [
|
|
ready('Decision Dashboard', `${B}/decisions`),
|
|
ready('Decision Register', `${B}/decisions/register`),
|
|
ready('Decision Workspace', `${B}/decisions/workspace`),
|
|
ready('Scenarios', `${B}/scenarios`),
|
|
ready('Assumptions', `${B}/assumptions`),
|
|
ready('Action Plans', `${B}/action-plans`),
|
|
ready('Outcome Reviews', `${B}/outcome-reviews`),
|
|
ready('Opportunity Inbox', `${B}/opportunities`, { releaseStage: 'a4' }),
|
|
ready('Opportunity Pipeline', `${B}/opportunities/pipeline`),
|
|
planned('Eligibility & Fit', `${B}/opportunities/fit`, 'a4', 'Analiza de eligibilitate cu criterii si probabilitate estimata.'),
|
|
planned('Applications & Deadlines', `${B}/applications`, 'a4', 'Checklist, documente, termene si dovada de trimitere.'),
|
|
],
|
|
},
|
|
{
|
|
order: '07',
|
|
label: 'Relationships & Community',
|
|
icon: 'relationships',
|
|
releaseStage: 'a3',
|
|
workspaceTypes: ALL_WORKSPACES,
|
|
children: [
|
|
ready('Relationship Dashboard', `${B}/relationships`),
|
|
ready('People', `${B}/people`),
|
|
ready('Organizations', `${B}/relationships/organizations`),
|
|
ready('Relationship Map', `${B}/network-map`),
|
|
ready('Interaction Timeline', `${B}/interactions`),
|
|
ready('Follow-ups', `${B}/follow-ups`),
|
|
ready('Commitments & Promises', `${B}/promises`),
|
|
planned('Introductions', `${B}/introductions`, 'a4', 'Intermedieri cu consimtamant explicit si rezultat urmarit.'),
|
|
planned('Communities', `${B}/communities`, 'a4', 'Componenta 15 (Community & Professional Network), neinceputa.'),
|
|
planned('Professional Network', `${B}/professional-network`, 'a4', 'Retea profesionala, contributii si recomandari.'),
|
|
],
|
|
},
|
|
{
|
|
order: '08',
|
|
label: 'Trust & Reputation',
|
|
icon: 'trust',
|
|
releaseStage: 'a4',
|
|
workspaceTypes: ALL_WORKSPACES,
|
|
children: [
|
|
ready('Trust Dashboard', `${B}/trust`),
|
|
planned('Credibility Profile', `${B}/trust/credibility`, 'a4', 'Fiecare factor afiseaza valoare, sursa, data, metoda, confidence si drept de contestare.'),
|
|
planned('Social Reputation', `${B}/trust/social`, 'a4', 'Contributii si feedback. Interzis explicit: scor social universal, monitorizare ilegala, acuzatii neverificate.'),
|
|
ready('Professional Reputation', `${B}/trust/professional`),
|
|
ready('Credentials', `${B}/trust/credentials`),
|
|
planned('Projects & Outcomes', `${B}/trust/outcomes`, 'a4', 'Rezultate masurabile, publicabile doar cu permisiunea clientului.'),
|
|
planned('References', `${B}/trust/references`, 'a4', 'Recomandari verificate, cu permisiune de publicare.'),
|
|
planned('Community Contributions', `${B}/trust/contributions`, 'a4', 'Mentorat, workshopuri, voluntariat, cu dovezi.'),
|
|
ready('Compliance', `${B}/compliance`),
|
|
ready('Outcome Reviews', `${B}/outcome-reviews`),
|
|
planned('Incidents & Disputes', `${B}/trust/disputes`, 'a4', 'Dispute cu drept de raspuns si contestare.'),
|
|
planned('Credit Readiness', `${B}/trust/credit-readiness`, 'a4', 'Pregatire pentru finantare. NU e scor de credit oficial (exclus explicit din blueprint).'),
|
|
ready('Trust Passport', `${B}/trust/passport`),
|
|
],
|
|
},
|
|
{
|
|
order: '09',
|
|
label: 'AI & Automations',
|
|
icon: 'ai',
|
|
releaseStage: 'mvp',
|
|
workspaceTypes: ALL_WORKSPACES,
|
|
children: [
|
|
planned(
|
|
'AI Executive Assistant',
|
|
`${B}/assistant`,
|
|
'mvp',
|
|
'AI Gateway exista si Hermes ruleaza izolat pe Hetzner, dar ceo-api nu expune inca un server MCP cu uneltele CEO OS -- agentul nu poate atinge datele tenantului.',
|
|
),
|
|
ready('Agent Center', `${B}/agents`),
|
|
ready('Workflow Library', `${B}/workflows`),
|
|
ready('Automation Builder', `${B}/automations`),
|
|
ready('Approval Queue', `${B}/ai/approvals`),
|
|
ready('Execution History', `${B}/ai/history`),
|
|
ready('Scheduled Actions', `${B}/ai/scheduled`),
|
|
ready('AI Context & Sources', `${B}/ai/context`),
|
|
ready('Costs & Usage', `${B}/ai/costs`),
|
|
],
|
|
},
|
|
{
|
|
order: '10',
|
|
label: 'Reports',
|
|
icon: 'reports',
|
|
releaseStage: 'mvp',
|
|
workspaceTypes: ALL_WORKSPACES,
|
|
children: [
|
|
ready('Executive Reports', `${B}/reports`),
|
|
ready('Business Reports', `${B}/reports/business`),
|
|
ready('Financial Reports', `${B}/reports/financial`),
|
|
ready('Life Reports', `${B}/reports/life`),
|
|
ready('Decision Reports', `${B}/reports/decisions`),
|
|
ready('Reputation Reports', `${B}/reports/reputation`),
|
|
ready('Accountant Reports', `${B}/reports/accountant`),
|
|
ready('Custom Reports', `${B}/reports/custom`),
|
|
ready('Exports', `${B}/reports/exports`),
|
|
],
|
|
},
|
|
{
|
|
order: '11',
|
|
label: 'Data Intelligence',
|
|
icon: 'data',
|
|
releaseStage: 'mvp',
|
|
// Spec: vizibil numai pentru Owner, Data Analyst si administratori autorizati.
|
|
// Rolul data_analyst nu exista inca in baza -> owner/admin.
|
|
permissions: ['owner', 'admin'],
|
|
workspaceTypes: ALL_WORKSPACES,
|
|
children: [
|
|
ready('Data Overview', `${B}/data`),
|
|
ready('Dataset Registry', `${B}/data/registry`),
|
|
ready('Ingestion Jobs', `${B}/data/ingestion`),
|
|
ready('Data Quality', `${B}/data/quality`),
|
|
ready('Entity Resolution', `${B}/data/entities`),
|
|
ready('Companies Database', `${B}/intelligence/companies`),
|
|
ready('Contacts Database', `${B}/crm`),
|
|
ready('Enrichment', `${B}/data/enrichment`),
|
|
ready('Segments', `${B}/data/segments`),
|
|
ready('Data Sources', `${B}/data/sources`),
|
|
ready('Compliance', `${B}/data/compliance`),
|
|
ready('Export Control', `${B}/data/export-control`),
|
|
],
|
|
},
|
|
{
|
|
order: '12',
|
|
label: 'Integrations & Devices',
|
|
icon: 'integrations',
|
|
releaseStage: 'a3',
|
|
permissions: ['owner', 'admin'],
|
|
workspaceTypes: ALL_WORKSPACES,
|
|
children: [
|
|
ready('Integrations Overview', `${B}/integrations`),
|
|
ready('Email Integration', `${B}/integrations/email`),
|
|
ready('Calendar Integration', `${B}/integrations/calendar`),
|
|
ready('ERP & Accounting', `${B}/integrations/erp`),
|
|
ready('Document Systems', `${B}/integrations/documents`),
|
|
ready('CRM & Communication', `${B}/integrations/crm`),
|
|
ready('API Connections', `${B}/integrations/api`),
|
|
ready('Webhooks', `${B}/integrations/webhooks`),
|
|
planned('Devices', `${B}/devices`, 'a4', 'Device registry + pairing prin gateway local (BLE), nu direct din cloud.'),
|
|
planned('Telemetry', `${B}/devices/telemetry`, 'a4', 'Pair -> Consent -> Telemetry -> Normalize -> Observation -> Metric.'),
|
|
],
|
|
},
|
|
{
|
|
order: '13',
|
|
label: 'Privacy, Security & Audit',
|
|
icon: 'privacy',
|
|
releaseStage: 'mvp',
|
|
workspaceTypes: ALL_WORKSPACES,
|
|
children: [
|
|
ready('Privacy Center', `${B}/privacy`),
|
|
ready('Consent Management', `${B}/privacy/consents`),
|
|
ready('Roles & Permissions', `${B}/privacy/roles`),
|
|
ready('Delegated Access', `${B}/privacy/delegated`),
|
|
ready('Data Classification', `${B}/privacy/classification`),
|
|
ready('Audit Log', `${B}/privacy/audit`),
|
|
ready('AI Activity', `${B}/privacy/ai-activity`),
|
|
ready('Export & Deletion', `${B}/privacy/export`),
|
|
ready('Retention Policies', `${B}/privacy/retention`),
|
|
ready('Security Events', `${B}/privacy/security`),
|
|
],
|
|
},
|
|
{
|
|
order: '14',
|
|
label: 'Settings & Administration',
|
|
icon: 'settings',
|
|
releaseStage: 'mvp',
|
|
workspaceTypes: ALL_WORKSPACES,
|
|
children: [
|
|
ready('Personal Profile', `${B}/settings/profile`),
|
|
ready('Professional Identity', `${B}/settings/identity`),
|
|
ready('Workspaces', `${B}/settings/workspaces`),
|
|
ready('Members', `${B}/members`, { permissions: ['owner', 'admin'] }),
|
|
ready('Notifications Inbox', `${B}/notifications`),
|
|
ready('Notifications', `${B}/settings/notifications`, { releaseStage: 'a3' }),
|
|
ready('Language & Timezone', `${B}/settings/locale`),
|
|
ready('Billing', `${B}/settings/billing`),
|
|
ready('API & Developer', `${B}/settings/api`),
|
|
ready('Platform Administration', `${B}/settings/platform`),
|
|
],
|
|
},
|
|
];
|
|
|
|
const ITEMS_BY_ROUTE = new Map<string, { section: NavSection; item: NavItem }>();
|
|
for (const section of NAV_SECTIONS) {
|
|
for (const item of section.children) {
|
|
ITEMS_BY_ROUTE.set(item.route, { section, item });
|
|
}
|
|
}
|
|
|
|
export function findNavItem(route: string) {
|
|
return ITEMS_BY_ROUTE.get(route);
|
|
}
|
|
|
|
/** Filtreaza registry-ul dupa rol (meniul e role-aware, cerinta din spec §18). */
|
|
export function visibleSections(role: Role): NavSection[] {
|
|
return NAV_SECTIONS.filter((section) => !section.permissions || section.permissions.includes(role))
|
|
.map((section) => ({
|
|
...section,
|
|
children: section.children.filter(
|
|
(item) => !item.permissions || item.permissions.includes(role),
|
|
),
|
|
}))
|
|
.filter((section) => section.children.length > 0);
|
|
}
|
|
|
|
export function countByStatus(role: Role) {
|
|
let ready = 0;
|
|
let planned = 0;
|
|
for (const section of visibleSections(role)) {
|
|
for (const item of section.children) {
|
|
if (item.status === 'ready') ready += 1;
|
|
else planned += 1;
|
|
}
|
|
}
|
|
return { ready, planned, total: ready + planned };
|
|
}
|
|
|
|
export const STAGE_LABEL: Record<ReleaseStage, string> = {
|
|
mvp: 'MVP',
|
|
a3: 'A3',
|
|
a4: 'A4',
|
|
};
|