# Phase 2 Bug Fix & Tweaks - Implementation Plan ## 1. Admin Panel: Tenant Creation, Contract/Plan Fields, Disable/Archive ### Database Changes - Add `contract_number VARCHAR(100)` and `plan_level VARCHAR(50) DEFAULT 'standard'` to `shared.organizations` (live DB ALTER + init SQL) - Add `archived` to the status CHECK constraint: `('active', 'suspended', 'trial', 'archived')` - Add to Organization entity: `contractNumber`, `planLevel` columns ### Backend Changes - **admin.controller.ts**: Add two new endpoints: - `POST /admin/tenants` — Creates org + first user + tenant schema in one call. Accepts: org name, email, address, contractNumber, planLevel, plus first user's email/password/firstName/lastName. Calls OrganizationsService.create() then sets up the user. - `PUT /admin/organizations/:id/status` — Sets status to 'active', 'suspended', or 'archived' - **auth.module.ts**: Import OrganizationsModule so AdminController can inject OrganizationsService - **auth.service.ts**: In `login()`, after loading user with orgs, check if the default org's status is 'suspended' or 'archived' → throw UnauthorizedException("Your organization has been suspended/archived") - **users.service.ts**: Update `findAllOrganizations()` query to include `contract_number, plan_level` in the SELECT ### Frontend Changes - **AdminPage.tsx**: - Add "Create Tenant" button → opens a modal with: org name, address, email, phone, contract number, plan level (select: standard/premium/enterprise), first admin email, first admin password, first/last name - Orgs table: add Contract #, Plan Level columns - Orgs table: add Status dropdown/buttons (Active/Suspended/Archived) per row with confirmation - Show status colors: active=green, trial=yellow, suspended=orange, archived=red ## 2. Units/Homeowners: Delete + Assessment Group Binding ### Backend Changes - **units.controller.ts**: Add `@Delete(':id')` route - **units.service.ts**: - Add `delete(id)` method — checks for outstanding invoices first, then deletes - Add `assessment_group_id` to `create()` INSERT and `update()` UPDATE queries - Update `findAll()` to JOIN assessment_groups and return `assessment_group_name` ### Frontend Changes - **UnitsPage.tsx**: - Add delete button (trash icon) per row with confirmation dialog - Add Assessment Group dropdown (Select) in create/edit modal, populated from `/assessment-groups` query - Show assessment group name in table - When an assessment group is selected and no manual monthly_assessment is set, auto-fill from the group's regular_assessment ## 3. Assessment Groups: Frequency Field ### Database Changes - Add `frequency VARCHAR(20) DEFAULT 'monthly'` to `assessment_groups` table (live DB ALTER + tenant-schema DDL) - CHECK constraint: `('monthly', 'quarterly', 'annual')` ### Backend Changes - **assessment-groups.service.ts**: - Add `frequency` to `create()` INSERT - Add `frequency` to `update()` dynamic sets - Update `findAll()` and `getSummary()` income calculations to adjust by frequency: - monthly → multiply by 1 (×12/year) - quarterly → amounts are per quarter, so monthly = amount/3 - annual → amounts are per year, so monthly = amount/12 - Summary labels should change to reflect "Monthly Equivalent" for mixed frequencies ### Frontend Changes - **AssessmentGroupsPage.tsx**: - Add frequency Select in create/edit modal: Monthly, Quarterly, Annual - Show frequency badge in table - Update summary cards: labels → "Monthly Equivalent Operating" etc. - Assessment amount label changes based on frequency ("Per Month" / "Per Quarter" / "Per Year") ## 4. UI Streamlining: Sidebar Grouping, Rename, Logo ### Sidebar Restructure Group nav items into labeled sections: ``` Dashboard ─── FINANCIALS ─── Accounts (renamed from "Chart of Accounts") Budgets Investments ─── ASSESSMENTS ─── Units / Homeowners Assessment Groups ─── TRANSACTIONS ─── Transactions Invoices Payments ─── PLANNING ─── Capital Projects Reserves Vendors ─── REPORTS ─── (collapsible with sub-items) ─── ADMIN ─── Year-End Settings ─── PLATFORM ADMIN ─── (superadmin only) Admin Panel ``` ### Logo - Copy SVG to `frontend/src/assets/logo.svg` - In AppLayout.tsx: Replace `