This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
Developer release log
A compact audit trail of technical changes from UtopiaSpace Core, UtopiaSpace Mobile, UtopiaSpace Ops, Auto Posting, and BD Lead. Start with the checklist on each card, then use the metadata only when you need to trace the source pull request.
The checklist on each card explains what changed and why it matters.
The metadata strip keeps the source repo, source branch, target branch, wiki branch and merge SHA.
Latest updates from UtopiaSpace Core, UtopiaSpace Mobile, UtopiaSpace Ops, Auto Posting, and BD Lead, newest first.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
developmentUse this lane for work that has landed on the development release line and may still be moving toward production.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
A new documentType field ("payslip" | "voucher") is consumed from payroll. The frontend now defaults missing values to 'payslip', treats 'voucher' as a contractor payment voucher, and refuses to render the payslip template or allow PDF downloads. The repo documents the field and compliance reasoning in PAYROLL_CONTRACT.md. This change pairs with payroll PR chokchunynh/utopia-payroll#701; note edge function DIRECT-DB builds may omit the field until updated.
My Profile no longer renders the payslip layout for contract‑for‑service (CFS) workers. When payroll's /api/hub/get‑payslip returns documentType: 'voucher', the Own Payslip and Team Payslips tabs show a short Voucher notice and disable the PDF download instead of rendering or offering a payslip. This takes effect only once payroll includes documentType; until then behaviour is unchanged.
Resolved an issue where compiled supplier payments could incorrectly merge with newly added payments. This ensures that all supplier payments are processed accurately and independently, preventing data discrepancies and improving the reliability of payment processing.
Implemented fixes to enhance mobile responsiveness across key Finance UI components, including `Finance Launcher`, `BackchargeApplication`, and `SupplierPaymentApplication`.
Users will now experience improved mobile responsiveness when using the Finance Launcher, Backcharge Application, and Supplier Payment Request (SPR) Application, making them easier to use on mobile devices.
The Overtime Summary pages across various applications now display correctly and are fully responsive on mobile devices, providing a better viewing experience.
Resolved an issue that caused 'bad request' errors when tracking and processing supplier payments in the Work Space, improving reliability for financial operations.
Job log and outcome cards in Operation Efficiency now prominently display the order number at the top, making it easier to identify jobs. Customer name and service type are now shown as secondary context, and action buttons no longer duplicate the order number.
Updated `docs/database.md` to reflect changes and new structures related to Ordinary Leave allocation calculations and storage.
The system now accurately calculates annual totals for Ordinary Leave allocations, providing improved precision for HR Generalists managing leave.
Updated `docs/database.md` with relevant information, likely related to the Public Holiday leave deduction logic changes.
The system now correctly deducts Public Holiday usage from leave allocations, ensuring accurate leave balances for employees.
Removed the `isLocalLeaveCascadeHost` hostname gate, enabling the mobile-aligned Leave Application chooser in the `utopia-personal` application for all environments. This change involved modifying `cascade.ts` and `LeaveApplicationEntryPage.tsx` to ensure the new chooser path is correctly navigated. E2E tests were updated to cover the `?edit=` bypass.
The new mobile-aligned Leave Application chooser is now available to all users. When applying for leave, you will now see a step-by-step chooser interface instead of the legacy inline form. This improves the user experience for submitting leave requests.
The User Access editor has been improved to allow for more precise control over permissions. Revoking an app tile can now automatically cascade and revoke associated workspace grants, with a clear confirmation dialog before saving. This prevents stale workspace grants from remaining active after an app tile is removed.
The HR Generalist workspace now has independent access control from the general HR App tile. This allows for more granular permissions, ensuring users only get access to the HR Generalist features when explicitly granted, preventing unintended over-permissioning.
Updated changelog entries in `utopia-launcher` and `utopia-work` applications. This release promotes a fix for the Shift Roster edit button visibility.
The edit button for Shift Rosters in the Work Space now displays correctly, improving usability for managers and schedulers.
Operation Efficiency PWA push notifications now support deep linking. Tapping a notification will directly open the associated job screen, even on a cold start, by leveraging `web_url` in the push payload. The base URL is configured via `oe.notifications.ops-app-url`.
Resolved an issue where Shift Roster drafts were incorrectly displayed as published, ensuring accurate status visibility.
Dates in the Ops Efficiency space now use a shorter format, and order links are now displayed in the TechRow component for better visibility.
Significant enhancements to the Shift Roster feature have been released across Utopia Work, HRMS, and Personal applications.
The Work app now includes new features for Overtime Approvals, such as per-row and select-all checkboxes, an action bar for Approve/Reject/Clear, and a confirmation dialog with mandatory remarks for rejections. Updates are now guarded to prevent overwriting already actioned requests.
Released new versions for Utopia Work (2.5.0), HRMS (2.7.0), and Personal (2.5.0), incorporating recent feature work and changelog updates. The launcher manifest has also been regenerated.
Managers can now use a tick box to approve overtime requests, streamlining the approval process.
A new Shift Roster report is now available under Work → Reports, enabling managers to view and manage employee shift schedules.
Resolved an issue where the Sales application failed to build on Vercel due to a missing `@types/node` dependency. This dependency is now explicitly declared, ensuring successful TypeScript validation during Vercel deployments.
Resolved a production build failure for the Sales application by adding a missing `@fontsource-variable/inter` dependency to its `package.json`.
This release cut includes version bumps for hrms (2.6.0), personal (2.4.0), work (2.4.0), finance (2.4.0), launcher (2.4.0), and root (2.0.6). Key fixes include: improved pagination for HRMS Leave Allocation/Summary to correctly display all employees; HRMS Leave Allocation now allows saving with blank leave types; and a fix for forms containing currency fields that previously prevented submission.
Resolved an issue where users could not submit applications due to problems with the currency input field.
HR Generalists can now allocate leave without encountering row limits. The system also correctly updates existing leave records, preventing duplicate entries and ensuring accurate leave entitlements.
The `docs/database.md` file has been updated to reflect recent changes in the database schema and related technical information.
Managers now benefit from a streamlined leave approval process, providing better tools for reviewing and acting on employee leave applications.
HR Generalists will find improvements in the leave acknowledgement process, making it easier to manage and track employee leave requests.
Employees can now utilize a new leave cascade feature for streamlined applications. The leave application flow has been updated to support gender-specific leave types and offers an improved display of leave history.
The parent-brand verifier has been extended, and new Chromium regression coverage has been added to ensure consistent brand identity across applications, including PDF rendering.
The protected Utopia Holiday Worry-Free Living offer-letter asset has been restored for use by HR recruiters.
Payslips and commission PDFs in your Personal Space now display the updated Brand CI v2 red-square/blue-triangle wordmark for improved consistency.
Introduced a new backend notification ingest endpoint and associated configuration properties, including support for OneSignal integration.
Enhanced the system to correctly process and display links for both LG and regular orders across Ops Efficiency features like Job Logs, Outcomes, and Susun Trip.
Currency input fields across all workspaces now feature an input mask, providing a more consistent and user-friendly experience when entering monetary values.
The Operation Efficiency space now includes a calendar feature, allowing users to easily monitor employee leaves.
Centralized the generation of Encik Beku order links within the Ops Efficiency space to ensure correct navigation and prevent links from pointing to localhost in production environments.
Updated the backend configuration for HTTP request header size in the Ops Efficiency space to correctly apply the 64KB limit, resolving potential issues with large headers.
Increased the maximum HTTP header size for the Operation Efficiency (OE) backend to resolve HTTP 400 errors encountered during authentication resolution, particularly for users with larger session data.
Implemented a new Hub SSO identity broker for the Operation Efficiency module, enabling Just-In-Time (JIT) provisioning and resolving Business Unit (BU) access. This update also includes a fix to replace `MultipartBodyBuilder` with `LinkedMultiValueMap` to prevent `NoClassDefFoundError`.
Resolved an issue where CI builds would fail due to an unauthorized Nx Cloud workspace. Nx is now configured to run locally in CI, preventing build failures.
Resolved a local development issue for the Encik Beku API where client-side calls failed due to incorrect cookie domains. The local Caddy configuration for Encik Beku API now mirrors production's parent/child host structure (`api.encikbeku.lvh.me`). This required updating `Caddyfile` and `tools/setup-https.js` to include `*.encikbeku.lvh.me` in the mkcert SAN list. Developers with existing local setups must regenerate their certificates by running `rm -rf certs/ && npm run setup:https`.
Implemented new Caddy hosts for Encik Beku's shared domain SSO, added Vercel deployment configuration for the Sales app, and clarified environment variables. Corrected a stale comment in `OeProxyController` regarding Supabase project usage.
Revised the SSO documentation to clarify the three different authentication mechanisms, including parent-domain cookie SSO for seamless integration.
Added new `sales.app.access` and `sales.encik-beku.view` grants to control access to the Sales application and the Encik Beku workspace. These grants are managed via the User Access editor.
Introduced the new Sales application, which includes a workspace picker to access the Encik Beku business unit. Access to the Sales app and Encik Beku workspace is controlled by UtopiaSpace grants.
The changelog has been updated to reflect the fix for the scrollable company dropdown in the HRMS calendar.
The company dropdown in the HR calendar can now be scrolled, resolving an issue where some options were inaccessible.
Implemented new mobile inbox and pairing controllers with DTOs and integrated OpenAPI/Swagger for API documentation. The unused `/oe/mobile` Spring facade was removed for cleanup.
The Susun Trip dispatch board now features a technician filter panel and an unassigned jobs count badge. A new 'Tech Updates' view has been added to display technicians' field outcome reasons. The Job Logs page has also received enhancements.
A new entry point has been added within the application, providing developers with direct access to relevant Wiki documentation.
Cut the 27th July 2026 release, incorporating 15 non-merge commits. This release includes version bumps for hrms (2.4.0 -> 2.5.0), personal (2.2.0 -> 2.3.0), finance (2.2.1 -> 2.3.0), work (2.2.1 -> 2.3.0), launcher (2.2.1 -> 2.3.0), and root (2.0.4 -> 2.0.5). All app changelogs were updated, and the launcher 'What's New' manifest was regenerated. Deploy notes include applying hrms and Resigned-status migrations, redeploying company-directory and get-payslip edge functions, and regenerating finance `spring-schema.d.ts`.
Resolved an issue that caused a 'bad request' error when approving supplier payments.
A new 'Resigned' user status has been added, allowing limited access to Utopia Personal. This status is manually set by HR and requires specific Supabase migrations for RLS policies.
Employees with 'Resigned' status can now sign in to Utopia Personal to view their profile and payslips. Access to all other applications remains blocked.
The Advanced Salary approval feature has been removed from the HR Generalist approvals grid. The dedicated route for Advanced Salary approvals is no longer accessible.
Leave and Overtime entries now display consistent, easy-to-read reference codes (e.g., LV-YYMMDD-XXXX, OT-YYMMDD-XXXX) across all Work app surfaces, replacing inconsistent UUIDs. The Manager Leave History page has been revamped for a better user experience, including improved mobile display and updated 'Pending' status.
Previously, approval pending-count badges in the Work app and Launcher home screen could over-count General Claims and Supplier Payment for approvers with submitter-role filters. This fix ensures that these badges now accurately reflect the number of pending approvals by correctly applying the submitter-role filter, aligning the badge counts with the actual approval list pages. This resolves discrepancies where badges showed pending items not visible in the lists.
The overtime verification and approval process for HR Generalists has been updated to streamline workflows and improve clarity.
Users can now compile receipts within the Accounts Payable section of the Finance space, streamlining payment processing.
Resolved two issues in the Team Payslips feature: 1. Decoupled team leader access from the employee's `personal.payslip.view` permission; leader access now depends solely on HR assignment. 2. Introduced a distinct `delivery_disabled` signal from the `get-payslip` edge function (HTTP 404) when an active employee's payslips are unavailable due to delivery being off, displaying a clear 'Payslip delivery is turned off' hint in the UI instead of a generic empty state.
PDF exports for AP Supplier Payments now feature improved layout, including selectable text for bank receipts and invoices, and correctly scaled image attachments. Approval Status and Activity Log are no longer included.
The details for Supplier Payment Request (SPR) approvals are now fully visible, making the approval process clearer and more efficient for users.
The 'First Name' field has been updated to 'Full Name', and the 'Last Name' field is now 'Short Name' in employee personal information sections within HRMS.
An additional employment category has been added to employment details, providing more options for HR Generalists.
The 'submit all SPR to bank' button has been fixed and is now fully functional. Detail pages for Supplier Payments (SPR) and Backcharges now display as a continuous scroll, removing the tabbed interface for a smoother viewing experience. Bank filters have been renamed to 'Status' for improved clarity. The 'View' button now allows you to switch between column and row views, offering more flexibility in how you display data.
This release wave includes version bumps for Personal (2.2.0), HRMS (2.4.0), Finance (2.2.1), Work (2.2.1), Launcher (2.2.1), and OE (2.1.2). Key technical updates involve setting `NEXT_PUBLIC_SUPPORT_WHATSAPP_UTOPIA` env var, applying Supabase migrations (`20260720120000_pay_document_visibility.sql`, `20260721120000_team_payslip_access.sql`), deploying `get-payslip` and `commission-slips` edge functions, and redeploying the finance backend for CORS changes.
The 'Contact support' dialog now displays an updated WhatsApp support number for easier access to assistance.
Improved the stability and reliability of the shared login experience within the Operation Efficiency app.
Improved the stability and reliability of the shared login experience within the Launcher app.
Resolved an issue with SPR tracker visibility and improved the shared login experience in the Work app.
The Finance app's Accounts Payable section has been refined with an improved toolbar, sorting options, batch loading, and claims processing.
HRMS users now have improved access to pay documents and team payslips, streamlining payroll and team management.
The Personal app now includes dedicated tabs for Payslips, Commission Slips, and Team Payslips, making it easier to access your payment information.
The login 'Contact support' dialog now correctly displays a dialable WhatsApp support number. Previously, it showed 'Unavailable'. This update involves setting the `NEXT_PUBLIC_SUPPORT_WHATSAPP_UTOPIA` environment variable and refactoring shared UI components for consistent display across all applications.
Introduced new `get-payslip` and `commission-slips` edge functions to securely retrieve pay document data from external payroll systems. These functions handle JWT verification and server-to-server communication using service secrets.
HR Generalists can now manage which employees have access to view their payslips and commission slips. Additionally, team leaders can be granted access to view payslips for their team members.
Users can now access dedicated tabs in My Profile within the Personal app to view their payslips and commission slips.
The Account Supplier Payment Verification table now loads all rows in batches, improving performance. You can now filter and search across all loaded data, and sorting and pagination behave more consistently. Sorting has been disabled for composite columns.
Fixed an issue that caused incorrect display or behavior in the Accounts Payable supplier payments table, ensuring accurate and reliable data presentation.
Fixed an issue where Accounts Payable Claims were not consistently displayed in the correct order.
Implemented updates to CORS configuration and enhanced error handling mechanisms within the Utopia Finance backend, improving API request control and system robustness.
Resolved an issue where saving profiles or changing a user's company in HRMS would fail due to orphaned database triggers. A new migration removes these unused `ops_profiles` triggers and related functions, ensuring profile edits now succeed.
The Accounts Payable Claims page now includes a 'Company' column, allowing users to view company information directly within the claims list.
Resolved an issue where the Supplier Payment Request (SPR) tracker was not consistently visible within the `ManagerSupplierPaymentHistory.tsx` page in the Work application's Manager Space.
Discover the latest updates across all applications in the new unified What's New Release Center, accessible from the Home header. This page features a timeline view, search, and per-app filtering.
The HR Employee List now includes a pending-count badge, a sortable 'Last Updated' column, and improved grouping of employees by status. Resigned employees are now correctly labeled.
Employees now have a Contract End Date field in their Employment Details, visible and editable on their detail page.
Implemented a system-wide rule to hide inactive and resigned users from people pickers, directories, and manager dashboard counts across Launcher, Work, Personal, Finance, and OE applications. This ensures users only interact with active personnel in selection interfaces, while preserving historical records and administrative visibility in HR tools.
Resolved an inconsistency where the Home app's approvals tile displayed an incorrect count compared to the Work app. Approval counting logic has been centralized into a new shared package (`@utopia/approvals`) to ensure accurate and consistent pending approval totals across both applications. This also involved removing several unused approval-related hooks.
The Live Attendance and Punch State Admin features have been removed from the HR Generalist attendance hub.
Optimized the loading speed for Supplier Payment Requests (SPR) within the Account Space and Finance Manager Space, resolving previous API performance issues.
The Supplier Payment Verification and Approved Supplier Payments tables have been updated with a new layout that utilizes the full desktop width. Approved Supplier Payments now also clearly mark receipt-uploaded payments as Completed.
The Supplier Payment Request (SPR) tracker in the Work application has received UI/UX enhancements. Users can now view bank receipts directly from the supplier payment history.
The Backcharge and Supplier Payment applications within Personal Space now offer improved mobile responsiveness, making them easier to use on various mobile devices.
Resolved a backend error by renaming the `work_locations` database table to `depot_name`.
HR Generalists can now enable or disable geofence mode for users, allowing for enhanced location tracking capabilities.
Fixed an issue with the `ops_profiles` sync trigger that was preventing profile edits by correcting column mapping and backfilling stale rows.
HR Generalists can now upload and remove employee profile pictures directly from the employee detail page. Additionally, the Company selector in the Work Information editor is now a searchable dropdown, improving usability for organizations with many companies.
Updated CORS settings for `admin-set-role` and `company-directory` edge functions to include additional production and staging hosts, resolving access issues for these environments.
The system now more broadly recognizes HR Generalists by including additional department, position, and team criteria, ensuring accurate role identification.
User membership handling has been improved to prevent creating duplicate entries when a user already has an active membership for a company.
HR Generalists can now successfully save changes when editing employee profiles. Previously, edits appeared to save but did not persist.
Users with access to the HR app can now directly edit employee information. The separate 'HR Generalist' permission toggle has been removed, simplifying HR role management as edit rights are now automatically included with HR app access.
The 'Operations Attendance' section has been renamed to 'Attendance Records' for clarity across various applications.
Managers can now use a 'My Team' filter when reviewing claims approvals, making it easier to manage requests from their direct reports.
The User Access editor in the Work app now prompts you to confirm before navigating away from unsaved changes, preventing accidental data loss.
The Work app now includes the User Access Roster and ReplyBox Dashboard/Contacts, centralizing developer tools within the Work environment.
The Developer, Work, and Admin sections are now exclusively available within the Work app. These sections have been removed from the Personal app's sidebar.
The agentic development workflow now includes a Playwright E2E verification loop across all active frontends (HRMS, Finance, Launcher, OE). This enables agents to build features and verify them in a real browser before shipping. A new `/verify-feature [app]` Claude Code command is available, and documentation for agentic development has been updated.
The redundant 'Business Units Assigned' field has been removed from profile forms. Internal dropdown components were standardized across profile sections. New Playwright end-to-end tests have been added for the registration and login flows.
Users with pending accounts are now securely confined to the `/pending` page until an administrator activates their account. The `/pending` page now instantly updates and grants access to the application once your account is activated.
The self-service registration form now allows you to provide your organization placement and an optional profile picture. All profile sections (Personal, Work, Financial) now use improved dropdowns for easier data entry.
HR Generalists can now manage and allocate leave for Official Leave (OL) and Public Holidays (PH) using an updated, more flexible logic.
The 'Total Hours' column in the Overtime Verification feature now displays accurate calculations.
The application now integrates with Replybox, allowing users to fetch and manage contacts and their associated tags. New dashboards for Replybox contacts are available in both Personal Space and the Launcher.
Resolved an issue where the total overtime hours were not always displayed correctly in the Overtime Approval and Details pages for managers.
New user access configurations have been introduced, enabling managers to auto-approve Supplier Payment Requests (SPR) and streamline financial workflows.
- Added PDF export for benefit claim verification details. - Fixed AP Claims amount column to show approved totals instead of submitted. - Corrected wording on Accounts Payable issued account amount cards. - Fixed display of benefit verification issued account amount cards.
The User Access editor now requires explicit confirmation to save changes. Edits are first drafted, and a sticky save bar appears, allowing you to review and confirm changes before they are applied. This prevents accidental immediate changes to user access.
Resolved an issue with the general claim button for account verification, ensuring smoother claim processing within your account space.
Resolved an issue that prevented manager auto-approval for supplier payment applications from working as expected, streamlining the approval process.
Added new documentation detailing database structure, migrations, and schema updates related to user data scopes and work attendance features.
Resolved a hydration crash affecting sidebar user menus across all applications and fixed duplicate import issues that prevented `director` and `launcher` builds.
Implemented new user access and data scoping capabilities, including company and department-level controls, to refine how data is viewed and managed across applications.
Introduced new attendance reporting features with company and department-level data scoping. Also fixed an issue that caused the attendance report page to become unresponsive.
The sign-in screens across all applications have been redesigned for a simpler, single-column layout. You'll now see 'Sign in with Google' as the primary option, with 'Sign in with email' available as a secondary link.
Replybox webhooks now utilize Remote Procedure Calls (RPC) for improved processing efficiency and reliability.
The option to apply for half-day leave has been removed from the leave application form.
Users can now select currencies when applying for backcharges, and backcharge details will display amounts with the chosen currency. Managers have an improved approval process to review individual backcharge items and recalculate request status.
Developers can now access a new dashboard to manage Replybox webhooks, streamlining the configuration and monitoring of integration events.
Users can now view their attendance records in the 'My History' section of their personal space.
HR Generalists can now manage petty cash with a new per-employee balance tracker. This update includes an employee picker for adding records, an editable transaction ledger with delete and supporting document features, pagination, and simplified list headers with hover tooltips.
The HRMS application has been updated to version 2.0.2. This release includes fixes for CORS issues and a nested sidebar button display. The updated version is now reflected in the application's sidebar and login screen.
Addressed a CORS issue that prevented role assignment in the HRMS app when running on local development hosts (`*.lvh.me`). Also resolved a nested button hydration warning in the HRMS sidebar user dropdown.
- Fixed the ordering of the employee list to show recent changes first.- Resolved an issue with the search bar in leave approval.- Updated Petty Cash: removed the category field and added 'Save' and 'Clear Filter' options.- HRMS now displays full names for employees and applicants.- Corrected the calendar format in employee details.
HR Generalists can now manage Overtime (OT) treatment within employment details.
HR Generalists can now delete leave applications directly from the HR Leave Acknowledgement page, enhancing flexibility in managing employee leave requests.
Implemented a multi-layered security enhancement to immediately sign out inactive or resigned users. This includes database changes to expose user status, real-time client-side session invalidation, backend JWT filter rejection, and reduced JWT expiry times for enhanced security. Also updated inactive account messages to 'contact HR'.
Cleaned up the wiki notification workflow by removing unused variables, improving maintainability.
Resolved an issue where the profile search functionality within the Manager Attendance Record was not working as expected.
The attendance module now includes a search bar, allowing users to easily filter and find specific user records.
Added the ability to view and manage resignation dates in employee profiles.
Resolved an issue where attendance records were not consistently displaying, ensuring accurate record-keeping.
Managers can now view attendance records more reliably and navigate through them with improved pagination in the Manager Space.
Users can now easily edit attendance records in the HR space using dedicated date and time pickers for clock-in and clock-out.
Users can now easily select clock-in and clock-out dates and times using a new date picker when managing attendance records.
developmentutopiaspace-mobile releases from development, so every PR merged here is a production change. Each update also refreshes the Mobile App pages when the change clearly belongs there.
developmentutopiaspace-mobile releases from development, so every PR merged here is a production change. Each update also refreshes the Mobile App pages when the change clearly belongs there.
mainutopiaspace-core releases from main, so every PR merged here is a production change. Each update also refreshes the UtopiaSpace pages when the change clearly belongs there.
mainutopiaspace-core releases from main, so every PR merged here is a production change. Each update also refreshes the UtopiaSpace pages when the change clearly belongs there.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
The repository dispatch workflow that notifies the Wiki sync now also triggers on push events to main and development (in addition to merged PRs). It skips deleted-branch pushes and avoids duplicate notifications when a push corresponds to an already-merged PR. The workflow sends a richer payload for pushes—including up to 20 recent commits and a trimmed list of changed files (up to 60)—and maps title/body/url/sha appropriately. It also adds read-only permissions for contents and pull-requests.
Removed an obsolete visual-check README and its Playwright screenshot fixtures used for payment-first detail pages. The change deletes docs/issue-566/README.md and a set of PNGs (desktop and mobile variants and history images), cleaning up stale test artifacts and reducing repo clutter. No runtime or user-facing behavior changed.
Work SPR history now renders as a view-only single scroll that places payment information and SPR ID before bank progress and attachments, with compact approval history at the end. Visual layout and differing-approved-amount highlights were added and exercised by Work e2e/playwright tests. This is a frontend UI change with no API or DB changes.
Accounts Payable backcharge details now show Backcharge ID, description, and payment details before bank progress and submission controls; attachments and receipts follow and a compact approval-history is placed at the end of the page. The change is UI-only and validated by Playwright fixtures and updated frontend tests; no API or database schema changes.
Supplier Payment (SPR) detail pages now lead with the SPR ID, description, and payment information before bank submission controls and attachments. Approval rows are condensed into a new compact approval-history component that highlights differing approved amounts while preserving actor, timestamp and remarks. Frontend-only change; verified by Playwright fixtures and e2e tests, no API or DB changes.
Managers can now select Post Overtime (Post OT) rows individually or with select‑all on desktop and mobile, and approve or reject mixed batches containing both Normal and Post OT. Canonical Post OT decisions run through the preview + atomic review RPC (review_post_ot_claim_v2) so server recalculation, early‑call settlement, roster updates, and audit logging are preserved. Failed rows remain selected and show per‑request errors for retry.
A new DB migration relaxes the supplier_payment_master.approval_gate_approval constraint to permit 'N/A' as a valid rollup value when every uncancelled payment type is rejected. Apply migration 20260918071240 before deploying the updated rollup service to avoid constraint errors.
Backcharge detail and manager pages now show Bank Submission and Receipt Upload as “N/A” when the approval gate is dead because all items or payment types were rejected. This avoids misleading “Pending” states on unreachable downstream steps. Backend migration 20260918071240 is required before backend deployment.
Supplier Payment detail and manager pages now display Bank Submission and Receipt Upload as “N/A” when the approval gate is dead (Rejected or N/A) because every payment type has been rejected. This prevents stages from remaining “Pending” for workflows that cannot be reached. Note: backend migration 20260918071240 is required before deploying the backend change.
The backend rollup logic was updated so payment types rejected at any stage are treated as dead ends. The recompute() logic now ignores fully rejected payment types when deciding stage rollups and sets accountApproval/approvalGateApproval to “N/A” when no active payment types remain. A new helper isRejectedPt() centralizes rejection checks. Deploy the accompanying DB migration before releasing.
When every payment type or backcharge item is rejected, the UI now shows downstream approval stages (Account/Finance Manager approval, Bank Submission, Receipt Upload) as “N/A” instead of “Pending.” Backend requires migration 20260918071240 before deployment. This affects detail and manager pages for Supplier Payments and Backcharges so users see a clear dead‑end state.
Backcharge approval logic was changed so items rejected at any stage are treated as dead ends and do not advance the pipeline. The backend adds new summarization rules that compute Account Status and Finance Manager (approval gate) status as 'Approved', 'Rejected', 'Pending', or 'N/A' based on managerApproval, verificationStatus, and approvalGateStatus across items. Front-end status fields (account_approval, approval_gate_approval) reflect these results.
A schema and code update makes 'N/A' a first-class approval value when a backcharge is killed upstream. A migration (supabase/migrations/20260917074347_relax_backcharge_master_approval_gate_check.sql) relaxes the approval_gate_approval constraint. API summarizers now return 'N/A' for killed items, BackchargeDecision includes 'N/A', and UI normalizers were adjusted. Run the migration during deployment.
Backcharge statuses now show "N/A" for Account and Finance stages when every item was rejected upstream (so those stages were never reached). Manager and personal backcharge detail pages, history rows, and step components display "N/A" instead of "Pending" in those cases; legacy finance_status values are still used as a fallback.
Fixes a production bug in the trigger public.trg_profiles_sync_supervisor_ids() that prevented assigning supervisors who are ordinary profiles (not rows in public.managers). The migration replaces min(p.id) on a uuid column with (array_agg(p.id))[1], and was applied via the Management API and recorded as supabase/migrations/20260921060000_fix_supervisor_trigger_min_uuid.sql (migration id 20260921060000). After the change 26 profile rows were updated and all active staff now resolve to supervisors.
Who can assign shifts is now determined exclusively by the Shift Roster feature in User Access. Role-name shortcuts (Manager/Supervisor/Admin) were removed, so User Access is the complete, authoritative list of roster editors. Admins should review and grant reports.shift_roster to staff who previously relied on role-based access.
The RPC update_profile_shift_time_for_roster and its gating policy were changed so only the reports.shift_roster grant (or hr.workspace.manage) authorises roster publish writes; the previous role-name shortcut was removed. A migration supabase/migrations/20260921090000_shift_roster_feature_access_only.sql implements this change—DB operators should apply the migration so the backend matches the frontend gate.
Shift roster editing is now allowed only for users granted the Shift Roster feature (reports.shift_roster); role names like Manager/Supervisor/Admin no longer grant roster edit access. The roster action button now always reads “Assign Shift” for managers to provide a consistent UI. Operators should ensure people who previously relied on role shortcuts receive the feature grant.
Added a new Playwright E2E spec (spr-approval-table.spec.ts) and test profile to validate currency precedence (invoice over request, MYR fallback), mobile wrapping, and table layout for SPR approval pages. Also refactored currency formatting in Manager/Director approval pages to use normalizeCurrencyCode and formatCurrencyAmount; Playwright config updated to run the new spec.
Manager and Director Supplier Payment Approval tables now show the stored invoice or request currency (invoice currency takes precedence, with MYR fallback) instead of a hardcoded MYR. Table values now wrap to avoid overlapping adjacent cells and long company or invoice text is contained on mobile cards, improving readability and preventing layout breakage.
ReplyBox exclusion directory is now live on Hub Production. The exclusion schema and three functions are active with both dashboard secrets set; the directory cut sequence 2 includes 626 entries (340 staff, 183 former, 112 line phones). Orphan membership was repaired, an hourly watchdog was armed, and every write is logged in the Hub ops ledger.
Updated the SHIPPED release log to reformat the ReplyBox exclusion directory record. The line now clearly lists the schema (`replybox_exclusion`), daily cut time (19:00 UTC), functions (`replybox-exclusion-snapshot/verify/sync`), scope (`rmb-rev-move`), migrations and merged PRs, and notes that the three functions return 503 `exclusion_unconfigured` until an Owner saves two dashboard secrets; coverage totals included.
Added a production release entry for the ReplyBox exclusion directory source. Introduces schema replybox_exclusion, a daily cut at 19:00 UTC, and new functions replybox-exclusion-snapshot/verify/sync. Two migrations were recorded on prod and three functions are active (v1) but currently return 503 (exclusion_unconfigured) until the Owner sets two required secrets. Coverage shows 626 phones and one orphan remaining.
Operators and developers: the coverage() function in the replybox_exclusion schema was changed so memberships whose auth.users row is soft-deleted (deleted_at IS NOT NULL) are excluded from orphan_membership_count. A new migration (20260919120000_replybox_exclusion_orphan_excludes_deleted_auth_users.sql) was added and applied; tests and fixtures were updated to seed a deleted and live auth.user and expect the adjusted orphan count. No UI changes.
Operator note: this PR adds three Supabase edge functions (replybox-exclusion-snapshot, -verify, -sync), a schema migration (20260910080000_replybox_exclusion_source.sql) that creates replybox_exclusion tables, and a shared runtime requiring HMAC keys and scope config. Scopes are disabled at install; perform the coverage review and enable specific scopes before go-live. The runtime expects REPLYBOX_EXCLUSION_HMAC_KEYS_JSON, REPLYBOX_EXCLUSION_SCOPES_JSON, SB_URL and a service role key.
Document the Hub-side ReplyBox exclusion source as a standalone reference: four data sources, immutable snapshot/pages, coverage counts, loading rules (work_phones), never-shrink behavior, and the go-live/bootstrap runbook. The page explains the Supabase migration and the guarded scope model and clarifies that all scopes are disabled at install until an explicit coverage review and enablement.
HR can now record a staff member's GitHub ID on their Employee Profile; staff see it read-only in My Profile. The field is optional, enforces GitHub handle rules (alphanumerics and hyphens, max 39), and requires a DB migration before rollout. Registration and profile-completion are unchanged.
Introduces a nullable text column profiles.github_id (max 39 characters) and includes migration supabase/migrations/20260901130000_add_github_id_to_profiles.sql. The migration must be applied before deploying the code that selects github_id; after applying, run db type generation to update packages/supabase-client/src/database.types.ts. No backfill is performed.
Adds an optional GitHub ID field to the Employee Profile in HRMS (Work Information). HR can add, change, or clear the value from HRUserApprovalDetails pages; clearing writes NULL. The field is validated against GitHub handle rules (letters, numbers, hyphens, no leading/trailing hyphen, max 39) and is optional so no backfill is required.
The vehicle register list (/asset/vehicles) no longer shows the single “Status” column. It now shows three columns — Road tax, Insurance and Puspakom — that display the same dated verdict shown on the vehicle detail page (e.g. “Expires in 7 months” / date, “Expired 28 days ago”, “Exempt”, or “No renewal on file”). The Status filter and saved ?status= links keep working; the new columns are unsortable and capped for layout so they stack on phones.
Developer-facing: the pay-document download flow was refactored so the app fetches payroll-rendered PDFs for preview rather than immediately saving. New API in use-payslip-data: fetchPayDocument (returns PayDocument with object URL), printPayDocument (opens browser print preview via hidden iframe and returns cleanup), and releasePayDocument (revoke object URL). Components and tests were updated to preview before save; callers must release the object URL when done.
Payment vouchers now open the browser's print / Save-as-PDF preview before anything is written to disk, matching payslip behavior. The preview shows the exact PDF bytes supplied by payroll (not a re-render). The in-app voucher view was restyled to use the payslip view vocabulary (same Card sections and emphasised total) while preserving payroll-supplied content and labels.
The get-payslip edge function now accepts action='pdf', forwards the request to payroll, and records delegated downloads in the same audit trail used for delegated views. In DIRECT-DB mode the function now returns 503 for 'pdf' (it cannot render pay documents). Merging this client change requires utopia-payroll#721 to be merged and deployed first; a missing payroll renderer will make the download fail with an explicit error.
Contractors can now download the payment voucher file that payroll renders instead of a locally-built payslip PDF. The Download button fetches payroll's PDF for vouchers (shows a “Preparing…” state and surfaces an error on failure); employees remain unchanged and still use the local payslip template. Note: this depends on the payroll service change (utopia-payroll#721) being deployed first.
A required migration (20260917090000_profiles_shift_time_open_time.sql) adds the literal 'Open Time' to profiles.shift_time validation and updates the roster-publish function to skip Open Time profiles. Apply the migration before deploying; without it saving an Open Time value will be rejected. Use npm run db:push (dev) and npm run db:push:prod (production) to apply.
Rosters now treat an employee with Working Time = Open Time as manager-assigned: roster views show empty days until a manager assigns a shift, and roster publishing no longer overwrites an Open Time profile with assigned hours. The auto-resolution logic now reads the profile's shift_time when deciding whether to pre-fill a day.
The employee profile Working Time field is redesigned as a three-way segmented control: Default (use Working Day), Set hours (preset ranges or inline custom From/To), and a new Open Time option meaning the employee has no set hours and their manager assigns each shift. Open Time is disabled for Privileged staff and the profile view now shows “Default (from <Working Day>)” when appropriate.
Developer note: the app now accepts and renders payroll's voucher block without recomputing values. A new Voucher type and shape-coercion are added to use-payslip-data, and VoucherDocument prints lines and shows payroll's payable as the total. The change affects normalizePayslip/use-payslip-data and the payslip UI; PDF generation for vouchers remains intentionally disabled. This requires payroll change utopia-payroll#719 and the edge function to forward the block (PAYROLL_SB_URL / PAYROLL_SB_SERVICE_ROLE_KEY can affect the path).
My Profile (own payslip) and Team payslip tabs now render a PAYMENT VOUCHER when payroll supplies a voucher block, letting contractors view the voucher instead of the previous notice. The voucher is printed byte-identical to payroll's lines, the document labels itself “Payment Voucher”, and the old VoucherNotice still falls back when payroll sends no block. PDF download for vouchers remains disabled.
Vehicles now include a Documents section showing grouped files (insurance, hire-purchase, invoices, assignments, etc.) with expiry, type and size. Authorized users can add documents via an upload dialog. The fleet team's ~2.3GB Drive archive is imported using a plan/apply backfill tool; ops must run the migration and the production plan/apply workflow after fleet review.
Adds migration supabase/migrations/20260915020000_asset_vehicle_documents.sql which creates the asset_vehicle_documents table and its constraints. Before running this in production follow the repo's checklist: apply the migration, regenerate database.types.ts from prod, run plan --target prod and have the fleet team review plan.csv/stale-compliance.csv before apply. The migration is designed so re-run is safe using source_path uniqueness.
Introduces a private vehicle-records storage bucket for sensitive documents (HP agreements, tax notices, large scans). The bucket is capped at 50MB and accepts PDF, images and Office files; links are returned as short-lived signed URLs rather than public object URLs. Client-side upload validation and new constants (RECORDS_BUCKET, MAX_RECORD_BYTES, RECORD_MIME) are added.
Adds a two-step backfill tool to import the fleet team's Drive archive. The plan step matches each file to a vehicle (folder then filename), classifies by name and extracts expiry dates into plan.csv and stale-compliance.csv for review. The apply step executes the reviewed plan idempotently: grant scans fill empty grant_doc_url, matching certificates fill empty compliance doc_ref, and all other files go into asset_vehicle_documents. TIF-to-PDF conversion and transient-retry logic are included.
Introduces asset_vehicle_documents to store vehicle papers that do not belong in grant_doc_url or the compliance doc_ref. Rows are one per document and source_path is unique so imports are re-runnable. Files live in a private vehicle-records bucket and are exposed via signed URLs. RLS requires asset.app.access for reads; adding mirrors vehicle write grants (asset.vehicles.manage or admin/manager/director).
Adds a Documents section to the vehicle detail page that lists every paper that has no tile of its own (past insurance, HP agreements, invoices, assignment papers, etc.). Documents are grouped by kind, show expiry/type/size, and include an Add document dialog for users with the Manage Vehicles grant. Files open through short-lived signed links from a private bucket.
Adds a bulk Revert Bank Submission for supplier payments (SPRBulkView). New POST /finance/supplier-payments/ap/batches/{batchId}/revert-submission reverts submitted payment types back to Pending, clears bankSubmittedAt/bankSubmittedBy/bankReceiptUrl but preserves bankSubmittedBank so resubmission can reuse the same bank. The action requires a non-blank reason and writes an activity log per request.
Introduces a batch-level Revert Bank Submission action for claims (ClaimBulkView). New backend POST /finance/claims/ap/batches/{batchId}/revert-submission reverts only claims with bankSubmitted=true back to Pending. bankSubmittedAt/bankSubmittedBy are retained as ledger audit metadata. The endpoint requires a non-blank reason and returns counts of reverted/skipped items.
Adds a batch-wide “Revert Bank Submission” action for backcharges (BackchargeBulkView). Backend POST /finance/backcharges/ap/batches/{batchId}/revert-submission was implemented; it deletes never-submitted reservation rows, detaches submitted rows from the batch (clearing batch id) and sets bankSubmitted=false while preserving bankSubmittedAt and bankSubmittedBank for audit. A non-blank reason is required and an activity log entry is written.
Supplier Payment Request (SPR) bulk views now show supplier/company bank details (bank name, registration number, account number) for each group and add copy controls. The page fetches compiled supplier payment views per company/supplier/currency (via /finance/supplier-payments/compile) and stores results by group to display bank fields inline during bulk review.
Claim bulk pages now surface applicant bank information (bank name, account number, account holder) grouped by applicant/company and add copyable bank fields. The implementation groups applicants, fetches per-claim details (rather than the compile endpoint) to resolve bank fields, and caches results per group so batch reviewers can confirm recipient bank details for claims in a batch.
Backcharge bulk pages now show company bank details (bank name and account number) for each payment group and add copy-to-clipboard controls for bank fields. The frontend fetches a company bank directory once and matches by company name (via an apiFetch to the companies endpoint) so operators can verify payout details when reviewing and processing backcharge batches.
Public note: Managers can now use a Quick edit card in Shift Roster to tick staff, pick one or several dates (span months), choose Working or Ordinary Leave, and Save straight to the published roster. Approved-leave dates are skipped and reported, drafts are updated where applicable, and time pickers now offer only :00 and :30.
Add documentation for the new Quick edit card in Shift Roster. Explain how managers can multi-select employees and dates, set Working or Ordinary Leave, and Save directly to the published roster; how prefill works for a single employee/date; skipping of approved leave and out-of-department staff; draft-update behaviour; and that Quick edit never changes the profile Working Time.
This change enforces EWD closure in the apps but does not change the database or policies. The Hub team should close or handle existing EWD rows and consider hardening DB constraints and policies: manager_edit_overtime_v1 still accepts 'Extra Work Day', overtime_requests.overtime_type has no check constraint, and insert/update policies currently allow any type. These gaps mean an API or migration is needed if you want DB-level enforcement.
The Hub no longer allows staff to apply for Extra Work Day (EWD). Personal and Work Overtime Application forms no longer offer the Extra Work Day type or days input; Submit and manager edit paths now refuse EWD with a clear message. HR can still filter and view historical EWD rows. Payroll will calculate EWD from attendance starting September 2026; no database migrations are included in this change.
Added a backend how-to for wiring a Business Unit (BU) into OE and updated the OE config examples: it describes X-OE-BU routing, the required application.yaml BU config block (name, base-url, token, unit-id), local and production env vars (BU_<CODE>_BASE_URL, BU_<CODE>_TOKEN, OE_BU_<KEY>_UNIT_ID), a curl-based verification step, and notes that blank base-url/token keep a BU inert.
Added developer-facing documentation for the Utopia OE app: a new OE README and a frontend LOCAL-README that explain how to run the frontend (Next.js/TanStack Router) and backend together (nx commands), ports (frontend :3003, backend :8081), the recommended local host (oe.lvh.me) for shared Supabase auth, launcher integration, and required environment setup for local development.
Reset on Asset Management > Vehicles now returns the register to its default Active view. It clears both column and global filters, hides the Reset button when there is nothing to clear, and includes an end-to-end check so the behavior stays consistent.
Vehicle records now support grant numbers, grant document links, Permit A, and PMA compliance tracking. The database change is additive, so existing records are not rewritten. Operator note: the migration was applied directly to production and development, and the Supabase types were regenerated from production.
Vehicle Registration & purchase now lets users record the grant number, upload a grant scan, and open the saved grant document. Permit A and PMA are tracked like road tax in the vehicle compliance tiles, and replacing an existing compliance document now updates the saved renewal instead of creating a duplicate-key failure.
Claim and leave forms now use the same date picker in Personal and Work. Users get a more consistent date selection experience, and the apps no longer need separate calendar implementations for the same workflow.
Users now see a consistent date picker when choosing claim or leave dates in Personal and Work. This keeps the two spaces aligned and makes date selection feel the same across both workflows.
Roster rules now live in one shared package, so Personal, Work, and HR resolve working days and working times from the same source. This reduces display differences between apps. Build note: local builds and CI should include the shared roster package wherever packages are precompiled or transpiled.
Employee profiles can now store working days separately from working times. This lets HR save custom time ranges without forcing every roster change into one field. Deployment note: apply the migration and review the new database checks before releasing UI that reads these profile values.
HR can now set both the days an employee works and the hours they work. Shift Roster views in Personal, Work, and HR honor those profile values, including custom “Others” time ranges, so manager and personal calendars show the same schedule.
A guarded migration adds the missing profile work schedule column only where it does not already exist. This prevents roster pages from failing with a missing-column error. Deployment note: run this migration before releasing the Post OT and Early Call-In manager review changes.
Shift Roster now uses the Working Time saved on each employee profile, including custom “Others” entries and Open/Flexi patterns. Calendar rows now match across Personal, Work, and HR, with a shared roster implementation helping keep the views aligned.
Adds a manager review workflow for Post Overtime and a new manager queue for Early Call‑In declarations. The web UI now includes review screens and list pages under /manager-space (early‑call‑in reviews and updated overtime details) that call preview_post_ot_manager_review_v1 and review_post_ot_claim_v2; Post OT rows are excluded from bulk approve and legacy edit paths. Deploy only after the accompanying DB migrations are applied.
The get-payslip contract now includes an optional documentType field ('payslip' | 'voucher'). Consumers should default to 'payslip' when the field is absent. When documentType === 'voucher' the frontend must not render a payslip layout; payroll renders vouchers and enforces forbidden wording. The repository now documents the field and explains why voucher rules must remain on the payroll side.
My Profile now avoids rendering a payslip when payroll marks a document as a payment voucher. The Payslip and Team Payslips tabs check payslip.documentType and show a new VoucherNotice component instead of the payslip layout; the PDF download is disabled for vouchers. This prevents displaying statutory/employment wording to contractors and preserves the prior behaviour until payroll sends documentType.
Certain users can now bypass Manager Approval for Supplier Payment Requests when they hold the new 'SPR Manager Approval Bypass (Unconditional)' grant. The bypass is enforced server-side and requires no client flag or scheduled-payment preconditions. Operators: a seeded grant was added by the migration; see the finance and policies docs for technical details.
A new ABAC policy key applications.supplier_payment.manager_auto_approve_unconditional was added and seeded. The migration supabase/migrations/20260911150000_spr_manager_auto_approve_unconditional_policy.sql inserts an abac_policy_metadata row and an allow row into public.user_policy_grants. The policy is GRANTED-style; possession of the grant is sufficient and is enforced server-side by the finance backend.
Server-side support for an unconditional Manager Approval bypass has been added to Supplier Payment Requests. The controller now checks a per-user ABAC grant (public.user_policy_grants) using a new UserPolicyGrant entity and UserPolicyGrantRepository and honors MANAGER_AUTO_APPROVE_UNCONDITIONAL_KEY; users holding the grant skip Manager Approval regardless of applicantType, scheduled dates, or client flags. Tests updated to inject the new repository.
Operators must redeploy the admin-update-auth-email Supabase edge function. The function no longer pages through auth.users to check email uniqueness (which produced 500s in production); it relies on updateUserById collision errors and matches GoTrue error messages with an isEmailTakenError helper. Redeploy with: supabase functions deploy admin-update-auth-email.
HR can change an employee's login email from the HR User Approval detail page. The Login Email card now writes the Supabase auth email immediately, and an open Edit Profile draft is updated to receive that new address so a later Save Changes does not restore a stale profiles.email. Note: this depends on redeploying the edge function (admin-update-auth-email).
Implemented backend and frontend support for a second daily attendance session, including a new `validateAttendancePeriod` function and a database migration. Enhanced testing infrastructure with a new isolated Playwright E2E project (`chromium-attendance-mocked`) and additional integration tests for attendance sessions.
HR Generalists can now add and edit up to two non-overlapping attendance sessions per employee per day. This feature includes robust validation to prevent identical, overlapping, or excess sessions, ensuring accurate time tracking.
Introduces a new Supabase edge function admin-update-auth-email (deploy with `supabase functions deploy admin-update-auth-email`) that runs on the service role, re-checks hr.workspace.manage server-side, and uses an explicit CORS allowlist. Also adds migration 20260909071152 which revokes public/anon/authenticated execute on public.admin_unlink_google_identity and grants execute only to service_role to restore intended permissions.
Adds an HR-only “Login email” card on the HR user-approval detail page that lets HR change an employee’s Supabase auth email, optionally sync the change into work/personal profile fields, and remove a stale Google identity. The write is performed via the service-role edge function and is gated by hr.workspace.manage; the UI only shows the control when the policy permits. Deploy the edge function before enabling this feature.
Manager-facing leave views now categorize applications into General, Medical, or Special Leave and show the full leave name per date in approval details. Approval detail pages omit duplicate Type and Period fields and use the new categorization for list filters and table headers. This improves clarity in Manager Leave Approvals and ManagerLeaveApprovalDetail pages.
The backend adds new Supabase RPCs and migrations to support Cascade v2 leave edits and authoritative previews. New DB functions include update_leave_cascade_general_v2 and preview_leave_cascade_edit_v2, and several migrations were added to update date handling and reason fields; these changes perform transaction-scoped day replacements and must be deployed before the frontend that calls the new RPCs.
Employees can now edit Cascade v2 leave requests (dates and notes) from Personal Space when manager review is pending or for future, manager-approved requests. Each edit fetches an authoritative server preview and triggers a secure server-side recalculation; resubmission returns the request to manager review. The Edit action and the Leave Application / Leave Details flows were updated to validate permissions and show authoritative previews.
A new ABAC policy asset.app.access gates access to the Asset Management space. The migration seeds the policy with no grants, so nobody can open the app until an access admin grants it. Explain how to grant the policy (Work app User Access editor or an SQL insert into public.user_policy_grants) and note that e2e/authenticated tests require the test user to hold this grant.
Document the new asset_vehicles register: it’s a server-side Postgres-backed list (search, filters, sorting and pagination run in Postgres) with ~506 rows (288 active in verification). The app reads free-text compliance values and splits/badges them in the UI. Also note the repository comment that current RLS/migration state is permissive in places and may require a follow-up tightening migration for true row-level restrictions.
The launcher app now serves Asset Management as a route subtree at /asset (no separate Vercel project or DNS needed). The Asset Management tile is live and gated by server-side access; its pages are lazily loaded so users who never open it don’t download assets. Playwright e2e specs for /asset/* were added; merging will redeploy the launcher, so be aware of the larger blast radius. Note: the deploy workflow references VERCEL_PROJECT_ID_ASSET (create a Vercel project and set that secret to avoid deploy failures).
The Finance sidebar order was changed so the SPR entry now appears above Backcharge in both the Application and Tracker navigation groups. This affects the visible menu ordering for finance managers but does not change routes or icons (e.g. /account-space/supplier-payment-application, /account-space/backcharge-application and the tracker equivalents). No backend or permission changes.
Adds automated PDF.js asset generation and verification to the Finance frontend build and deployment. The app now runs a pdfjs:assets script during predev/prebuild to copy CMaps, standard fonts and OpenJPEG/JBIG2 wasm decoders into public/pdfjs; the Vercel deploy workflow tests those files exist in the prebuilt static output and a new Playwright e2e checks they are served and non-empty before release.
Accounts Payable now treats “Create Bulk ID” as a grouping step for multi-item backcharge, claim, and supplier payment batches. The UI shows pending batch counts, moves batches awaiting “Submit to Bank” to the top, opens Bulk View after batch creation, and lets users add or remove pending requests before submitting the batch to the bank.
Finance backend now supports grouped AP batches for backcharges, claims, and supplier payments. Single-item submissions still submit immediately, while multi-item batches use generated IDs such as BCH-B, CLM-B, and SPR-B and remain pending until explicit submit-to-bank endpoints run. New add, remove, and submit batch requests preserve per-item results and prevent empty or invalid batches.
Users can now view the shift roster at a department level, providing a broader overview of team schedules and improving management of personal shifts.
Implemented enhanced search capabilities for `SupplierPaymentTracker` to include invoice number and amount. Added `dateRange` controls to `TrackerFilterBar` (for `createdAt`) and `DataTableToolbar` (for `dateSubmitted` in Submission History). New predicate logic is encapsulated in `shared/utils/trackerFilters.ts` with comprehensive unit tests. Verified functionality across various scenarios, including persistence of date bounds with existing Save/Reset mechanisms. All CI gates passed, including `nx test`, `nx lint`, typecheck, `nx build`, and `deps:verify`.
You can now search for supplier payments by invoice number and amount. Date filters have been added to both the Supplier Payment Tracker and Backcharge Tracker, as well as to the Submission History, allowing you to filter records by creation date or submission date respectively. These new filters persist with your saved search settings.
Implemented a fix to ensure proper rendering of PDF attachments, specifically addressing issues with CJK (Chinese, Japanese, Korean) text and non-embedded fonts for improved display accuracy.
You can now archive incomplete Supplier Payment Requests (SPRs) and provide a reason for archiving them.
Resolved recurring `Deploy Guard` failures by updating `deploy-launcher.yml` to automatically redeploy the `utopia-launcher` when any application's `CHANGELOG.md` or `package.json` is modified. This ensures the launcher's `/changelog` page is always up-to-date and prevents false positive `Deploy Guard` notifications. Additionally, `deploy-guard.yml` was enhanced to provide clearer diagnostics for deployment issues.
The attachment preview dialog previously inline in `AccGenClaimDetails.tsx` has been extracted into shared components: `src/shared/ui/attachment-preview-dialog.tsx` and `src/shared/ui/attachment-preview-list.tsx`. This refactoring enables auto-expansion and enhanced viewing (zoom, pan, rotate) for attachments on Supplier Payment and Backcharge verification pages, aligning them with the General Claims experience. Note that saving rotated attachments is deliberately disabled for SPR/BCH due to `backcharge-storage` RLS policies.
Attachments on Supplier Payment, Backcharge, and General Claims verification pages now auto-expand on load. A new 'View' action provides a comprehensive preview dialog with zoom, pan, and rotate capabilities. The 'Save' option for rotated attachments is currently disabled for Supplier Payments and Backcharges due to storage policies.
Removed 178 dead public assets (7.3 MB) from various applications' `public` directories, including `utopia-finance` and `utopia-hrms`. This cleanup targets assets that were no longer referenced by any active code or features, resulting in smaller application builds and improved efficiency.
A significant architectural refactoring was completed, consolidating redundant domain logic across the personal, work, hrms, and finance applications. This involved creating seven new shared packages (`@utopia/announcements`, `@utopia/petty-cash`, `@utopia/claims`, `@utopia/overtime`, `@utopia/dashboard`, `@utopia/backcharge`, `@utopia/supplier-payment`) from twenty-three duplicated copies, resulting in a 79% reduction in byte-identical domain code. This refactoring also surfaced and documented a defect in `claimApi` related to `id` column usage, which was present in unused functions. Several deliberate divergences in application behavior (e.g., petty-cash holder definitions, analytics chart rendering) were identified but not converged to avoid unintended production changes.
Users will now experience more reliable profile picture loading across Personal, Work, HRMS, and Finance apps due to improved URL handling. A fix was implemented to prevent duplicate notification toasts in OE and Finance, ensuring a cleaner notification experience. Additionally, benefit entitlements are now displayed more consistently in Personal Space.
Completed a major refactoring effort to consolidate shared infrastructure code, reducing redundancy from sixteen copies to four shared packages. This involved de-duplicating logic for profile pictures, notifications, feedback reports, and benefits across various applications. The change significantly reduced redundant lines of code and removed dead code, improving maintainability and setting a cleaner architectural baseline.
Introduced comprehensive end-to-end tests for command palette and sidebar consistency across Work, Finance, HRMS, Personal, and OE applications, including a new e2e suite for Utopia Work. This significantly improves UI reliability. Additionally, fixed an issue with the access gate path handling special characters and resolved a duplicate test key in `package.json`.
Resolved inconsistencies in how application features and navigation items are displayed based on user permissions. Command palettes and sidebar navigation across Work, Finance, Personal, and HRMS applications now accurately reflect server-authoritative access decisions, preventing users from seeing inaccessible pages or missing available ones.
The Supplier Payment Tracker's status filter now accurately reflects all possible payment statuses, including 'Paid', 'Pending Receipt', and 'Rejected by Account'. You can now filter all supplier payment requests effectively.
A major cleanup was performed in the Utopia Finance frontend, resulting in the deletion of 451 source files that were no longer reachable by the application's router. This effort improves code maintainability, reduces the codebase size, and ensures only actively used components are part of the build. The process involved careful analysis to determine live versus dead code, particularly for pages with `V2` variants and shared components like `Profile` and `rentalTracker`.
The updated Taskboard V2 is now the exclusive and default task management experience. All previous links to `/task-board` will automatically redirect you to the new and improved Taskboard V2, ensuring a consistent and modern interface for managing your tasks.
The original Taskboard (`TaskBoardPage.tsx`) has been fully retired and removed from all applications (Finance, Launcher, Personal, Work). The `/task-board` route now permanently redirects to `/task-board-v2`, ensuring all existing links and in-app navigation seamlessly use the modern Taskboard V2 implementation. This change involved removing over 14,000 lines of legacy code.
A new database migration has been added to remove the retired Toppie schema from the Supabase project. This migration drops 15 tables, including all `toppie_*` tables, `ai_sql_allowlist`, and `ai_sql_glossary`. It is not automatically applied and requires manual execution. Users should take a backup before running this migration.
The Operation Efficiency (OE) application now displays tables with proper row dividers, invalid form fields with clear error indicators, and dark-mode form fields with correct background fills. Icons in buttons and menus are now consistently sized, and the command palette styling has been restored. These changes fix a long-standing issue where certain UI elements were not rendering correctly, bringing OE's appearance in line with other applications.
We've updated the visual appearance and accessibility of several core UI components across six applications. You'll notice improved focus rings, subtle shadows on buttons and inputs, and a refreshed look for badges. Most notably, tooltips will now appear dark instead of light. These changes bring a more consistent and accessible user experience.
A new type checking ratchet has been implemented in the CI pipeline. This tool tracks TypeScript error counts per file and will prevent new errors from being introduced, ensuring continuous improvement in code quality. Existing errors can be fixed without failing the build.
The `utopia-admin`, `utopia-director`, `utopia-manager`, and `utopia-supervisor` applications have been removed. Their functionality was previously consolidated into the `utopia-work` application, so no user capabilities are affected. This change streamlines the codebase and removes unused infrastructure.
The `public.attendance` table now includes an `updated_at` column and a maintaining trigger. This allows data consumers, such as the Payroll system, to efficiently poll for changes using a cursor, eliminating the need for full table re-reads to detect edited attendance records.
Users can now export selected rows from the Account Summary and Tracker pages to an Excel file, enhancing data management and reporting capabilities.
The application's sidebar navigation has been improved to dynamically manage the visibility of menu items, providing a cleaner and more relevant user interface.
Supplier Payment Applications now feature an autosave function to automatically save your progress. Additionally, a new dialog will prompt you if you attempt to navigate away with unsaved changes, helping prevent accidental data loss.
The group-wide design token authority has moved to the Brand CI v3 registry (`ui.utopiaai.my`). This document remains authoritative for UtopiaSpace-specific design patterns, with future plans to reconcile token values for key components like `CurrencyInput` and `TimePicker`.
Bank receipts in Supplier Payment and Backcharge documents now appear before invoices and supporting documents. Additionally, requestor names in financial document headers (including Claims and SGS) now display a shorter, more user-friendly name when available, falling back to the full legal name.
Managers can now edit various details of an employee's overtime request, such as type, time, and break duration, directly from the approval page. Each edit requires a reason and is logged in the overtime history.
The HR overtime details page now includes an `OvertimeEditHistory` component, allowing HR Generalists to view a read-only, expandable list of all manager edits made to an employee's overtime application, complete with remarks and field changes.
Introduced a new `OvertimeEditHistory` UI component, comprehensive Playwright E2E tests for overtime edit history, and isolated PostgreSQL tests for manager overtime edits. This includes new database migrations to support atomic manager edits.
Managers can now edit various details of an employee's overtime application, such as type, time, and break duration, before approval. All edits are logged and visible to HR for transparency.
Introduced a new profile photo requirement for user registration, including robust photo handling, UI updates for confirmation pages, and a non-blocking prompt for existing users. This involved new `access-control` logic, `profile-pictures` components, `utopia-ui` elements, and database migrations (`20260902120000`, `20260902130000`). Comprehensive E2E tests (`registration-photo.spec.ts`) were added.
Users registering for Utopia Personal or Work apps must now upload a profile photo as part of the registration process. Existing users will also be prompted to add a profile photo to their account.
Implemented a UI refactor for the Manager Supplier Payment Request (SPR) approval route in `utopia-work`. Details, Payment, Invoice, and Activity are now displayed as continuous sections using an opt-in `DetailsShell` layout. This addresses a UI discoverability issue where critical information was hidden behind tabs, improving the manager approval workflow. Other `DetailsShell` consumers retain the tabbed layout.
Managers can now view all Supplier Payment Request (SPR) approval details, including Payment, Invoice, and Activity, on a single continuous page. This change improves discoverability and streamlines the approval process by eliminating the need to switch between tabs for critical information.
Implemented a refactor in the finance frontend to integrate Supplier Payment Request (SPR) and Backcharge attachments directly into their respective item cards. This change improves the user workflow for invoice verification by co-locating documents with itemization fields. Key files modified include `AccountBackchargeDetails.tsx`, `AccountSupplierPaymentDetails.tsx`, and `attachment-preview-list.tsx`.
Users can now view Supplier Payment Request (SPR) and Backcharge attachments directly within their respective item cards. This streamlines the invoice verification process by placing relevant documents alongside the itemization details, reducing the need for scrolling and switching sections.
Introduced new reusable `ZoomPanSurface` and `ZoomScrollSurface` UI components for image and PDF attachment previews. Updated Playwright configuration to increase e2e test timeouts and added new e2e tests for attachment zoom and pan functionality.
You can now zoom, pan, and rotate attachments in the Finance / Account Space General Verification preview. This makes it easier to read details on receipts and other documents without leaving the page.
Removed inert `Create React App manifest.json` files from `personal`, `hrms`, `work`, and `oe` apps that were not being used by Next.js. Updated internal code comments referencing the previously removed `CenteredLottie` component in `TableSkeleton` implementations across multiple applications. `CHANGELOG.md` has been updated to reflect these removals and changes.
The documentation for PWA standalone apps has been updated to accurately reflect that only the Launcher app currently ships with a `display: standalone` manifest. Previously, the documentation incorrectly stated that five apps had this capability, clarifying which applications offer installable PWA experiences.
Removed 15 previously committed files including JVM crash dumps, a pnpm store, a nested `package-lock.json`, a `.gitignore` backup, and duplicate `pwa-512x512 copy.png` images. New `.gitignore` rules were added for `.pnpm-store/`, `* copy.*`, and `*.local-backup` to prevent these types of files from being tracked in the future, improving repository cleanliness and build consistency.
This update significantly refactors the `@utopia/ui` package to improve application performance and dependency management. We've implemented `sideEffects: false` for packages and introduced per-entry-point exports for `@utopia/ui`, leading to reduced JavaScript bundle sizes (e.g., Utopia Sales `/sign-in` bundle reduced by 19%). A new dependency checking tool (`check-package-deps.mjs`) replaces the old one, ensuring more accurate dependency declarations and unblocking the sharing of common UI components like `DataTablePagination` and `DataTableViewOptions` across applications.
Resolved an issue with the login callback and ensured that resigned employees can correctly access their profile.
The core feature flag system has been refactored into a shared package, consolidating logic and removing redundant code across multiple applications (Finance, HRMS, Launcher, OE, Personal, Work). This includes a latent fix for the Utopia Launcher to correctly read feature flags instead of relying on default values, improving its future reliability. The system now explicitly requires a feature flag provider, preventing silent failures.
The core authentication infrastructure (`@utopia/auth`) has undergone a significant refactor, centralizing the sign-in journey and eliminating 410 lines of redundant code across applications. This resolved a critical bug where `callbackUrl` parameters were lost during sign-in, preventing correct redirection. The refactor also addressed a 'Maximum update depth exceeded' error and improved cold sign-in performance by optimizing imports.
Users will now be correctly redirected to the page they were attempting to access after signing in, instead of being sent to the launcher hub. This fixes an issue where deep links and session expiry would not return users to their intended destination, significantly improving the sign-in experience across all applications.
Consolidated `1,306` lines of duplicated authentication callback logic and `210` lines of duplicated Supabase client code into shared modules (`packages/auth`, `packages/supabase-client`). Introduced a shared Playwright contract for auth callback testing across all apps. Generalized the `check-package-peer-deps.sh` script. Also, 'Back to Sign In' now signs out first, and a missing `NEXT_PUBLIC_PERSONAL_URL` will now fail closed.
Resigned employees will now correctly access their profile page (`/settings/profile-v2`) across all applications after logging in, instead of being stuck on a 'registration pending' screen. This ensures limited access (view-only profile, payslips) is maintained as intended.
The sidebar button has received UI improvements for a more intuitive and visually appealing experience within the application.
Added detailed documentation to the CI workflow (`pr.yml`) explaining why end-to-end (e2e) tests are currently deferred from running in CI. The update outlines the technical mechanism for running e2e tests, the necessary Supabase credentials and environment variables, and the current blockers related to using a shared dev database and potential write operations. This clarifies the decision for future development without changing existing CI behavior.
Fixed a critical YAML syntax error in the `schema-catchup` GitHub Actions workflow. A new CI validation tool (`tools/check-workflow-yaml.mjs`) has been implemented and integrated into the CI quality job to automatically detect and prevent invalid workflow YAML from being merged, improving CI reliability.
A new scheduled CI workflow has been implemented to automatically detect and resolve database schema drift between the production and development environments. This workflow reads changes from production, generates database migration files, applies them to the development environment, and opens a pull request for review. Key safety features include production being read-only, no auto-merging of generated PRs, and destructive changes (like drops) being commented out for manual review. The workflow is designed to be safely re-runnable. Note that four new secrets (`PROD_DB_USER`, `PROD_DB_PASSWORD`, `DEV_DB_USER`, `DEV_DB_PASSWORD`) are required for this workflow to function.
The Supabase database migration process has been consolidated into a single `supabase/migrations` directory at the repository root. This update streamlines the workflow, enabling `supabase migration new` from any location and clarifying `npm run db:push` for development and `npm run db:push:prod` for production. This change resolves previous issues with `supabase db push` failing due to unrecorded migrations and replaces 151 scattered migration files with a single production-derived baseline.
Resolved a critical issue where environment variable values containing special characters were incorrectly parsed, leading to failures in `npm run types:generate -- --target prod` and preventing successful connections to production databases. This fix ensures correct handling of quoted environment variables.
A new read-only tool has been introduced to help identify and report discrepancies between the live database schema and the codebase's migration files. This improves database consistency and supports ongoing migration consolidation efforts by providing clear insights into schema drift.
The `utopia-work` application underwent a significant codebase cleanup. This included deleting 389 source files that were unreachable and retiring the `legacyTables` component. Two files (`OrderTableFeedbackReport` and `OrderListFeedbackReport`) that previously used `legacyTables` were refactored and moved to their respective feature directories. This internal maintenance improves code health and maintainability without affecting current user functionality.
A significant code cleanup was performed in the Utopia Personal application, removing 510 unreachable source files. This reduces the codebase size and improves maintainability for the `utopia-personal` app.
Performed a significant cleanup of the HRMS application codebase, removing 417 unreachable source files, including an unused `salary-advance` feature. This effort also led to improvements in the internal code reachability check, enhancing development tooling.
Removed 206 unreachable source files from the `utopia-oe-frontend` application, improving codebase maintainability without impacting product functionality.
The `utopia-launcher` application underwent a significant codebase cleanup, removing 636 unreachable source files. This change introduces a new reachability gate in the CI/CD pipeline to prevent dead code from being merged in the future, aligning with [ADR 0001](docs/adr/0001-frontend-source-must-be-reachable.md). This is an internal technical improvement with no user-facing changes.
Removed the `apps/utopiaspace-oe` directory and its leftover `next-env.d.ts` file. This directory was an unused remnant from a previous rename (`utopiaspace-oe` to `utopia-oe`), and its removal streamlines the codebase.
The ChatDaddy integration, including its OpenAPI client, associated Supabase Edge Functions (`notify`, `process-chatdaddy-queue`), and database queue (`chatdaddy_notification_queue`), has been fully retired. The `notify()` function in `src/shared/lib/notify.ts` has been stubbed to prevent runtime errors from existing call sites, ensuring smooth operation across applications while the integration is fully deprecated. This change removes a silently failing backend component and streamlines our notification infrastructure.
The consistently failing and unused DigitalOcean Container Registry (DOCR) backend deployment workflow (`deploy-do.yml`) has been removed from our CI/CD pipeline. This cleanup improves the reliability and signal of our CI/CD system by eliminating a workflow that never succeeded and was not part of the live backend deployment process. The `deploy-guard.yml` workflow was also updated to reflect this change.
The workspace's design documentation has been consolidated into a single `docs/design.md` file, replacing multiple disparate documents. This effort involved a significant rewrite, incorporating mobile/desktop design patterns and design token specifics. During this process, two critical build configuration bugs were identified and documented (though not fixed in this PR): a broken `@source` path in `utopia-oe` and inconsistent `components.json` styles across apps. Additionally, `utopia-oe`'s light-mode `--border` and `--input` tokens were aligned with other applications for visual consistency.
The design documentation has been consolidated into a single, comprehensive guide covering all seven UtopiaSpace applications, including detailed considerations for both mobile and desktop experiences. This update expands on layout principles, mobile-specific patterns, and clarifies design tokens. It also includes a minor visual fix for Utopia OE's border and input elements.
A significant UI refactor moved 19 common UI primitives (e.g., `alert`, `button`, `checkbox`, `table`) from `utopia-sales` into a shared UI package. This eliminates duplicate files and streamlines UI component management across applications. The `deps:verify` guard successfully prevented a potential production deploy break by catching undeclared Radix packages. Additionally, a type error in `time-picker` was fixed, resolving 12 type errors across six applications.
The CI deploy guard has been improved to ensure production reliability. Previously, it only checked if a deploy *started*. Now, it verifies if the deploy *succeeded*, preventing stale builds from reaching production. The guard polls for completion with a 20-minute deadline and reports distinct states for missing, failed, or unfinished deploys.
Addressed critical deployment failures in `utopia-sales` caused by undeclared `@utopia/ui` peer dependencies. This fix ensures `utopia-sales` correctly declares all necessary UI package dependencies and introduces a new CI guard (`tools/check-package-peer-deps.sh`) to automatically verify peer dependency declarations across all applications, preventing similar issues in the future. This significantly improves the reliability of our build and deployment pipeline.
A significant refactoring effort has moved 10 core UI primitives (including `accordion`, `dialog`, and `dropdown-menu`) from `shared/ui` into a new `@utopia/ui` package. This change eliminates 60 duplicate files and rewrites over a thousand import statements, resulting in a net reduction of nearly 4,000 lines of code. This internal architectural improvement enhances code maintainability and reduces duplication without introducing any user-facing changes.
Corrected the canonical names for 'Ibnu Sina Sdn Bhd' to 'Ibnu Sina Care Sdn Bhd' and 'Scaffolding Sdn Bhd' to 'Scaffolding Malaysia Sdn Bhd' within the system.
A new `deploy-guard.yml` workflow has been added to the CI/CD pipeline. This addresses a critical issue where large merges could cause GitHub Actions `paths:` filters to truncate, leading to deployments being silently skipped. The deploy guard now uses Nx to identify all affected projects and automatically dispatches any missing deployments, ensuring all necessary applications are updated and making any potential deployment gaps immediately visible.
Corrected outdated information regarding the release workflow. The documentation now accurately describes the manual process for bumping versions and updating the `CHANGELOG.md`, clarifying that previous `npm run release` commands and `tools/release.js` never existed.
Updated documentation for running applications, correcting development server ports for `utopia-finance-frontend` (now 3001) and `utopia-personal` (now 3000). Also, added `utopia-launcher` and `utopia-work` to the list of Supabase-only frontends and clarified which applications have dedicated `CLAUDE.md` files.
Updated the list of database migration directories to accurately reflect all existing migration paths for `utopia-finance`, `utopia-hrms`, and `utopia-oe` applications, ensuring developers can find all relevant migrations.
This update resolves several critical linting issues, including `no-unsafe-finally`, `no-constant-binary-expression`, `no-self-compare`, and `no-self-assign`, across the codebase. These four rules have now been promoted to `error` status, preventing future regressions. This also resulted in a reduction of 20 type errors.
We've fixed an issue in `utopia-work` where certain financial amounts might have displayed incorrectly as zero instead of showing the manager-approved value. Additionally, a bug preventing success styling from rendering correctly on submitted tasks has been resolved, ensuring visual clarity.
We've implemented a significant update to improve the stability and reliability of several applications, particularly in areas involving HR menus and petty cash details. This change resolves issues that could lead to unexpected behavior or crashes, ensuring a smoother experience.
Addressed 80 instances of conditional React Hooks usage across multiple applications, preventing potential `Rendered more hooks than during the previous render` crashes. The `react-hooks/rules-of-hooks` ESLint rule has been promoted from `warn` to `error` to enforce unconditional Hook calls and prevent future regressions.
A new fail-closed, default-dry-run production reconciliation process was implemented for historical Contra claim `CLG-260525-3D64`. This ensures serializable transactions with row locks, creates immutable receipt snapshots, and generates audit events for robust data integrity. A dedicated backfill tool (`tools/backfill-claim-clg-260525-3d64-contra.mjs`) was added to support this operation.
We've improved the system to accurately and completely preserve historical Contra claim receipts and reconciliation details. This enhances data integrity for past financial transactions, ensuring all records are precise and fully accounted for.
Unit tests across various applications are now reliably discovered and executed. Previously, tests were not always run due to hardcoded file paths in `project.json` configurations and a missing unit test job in the Continuous Integration (CI) workflow. This update introduces globbing for test targets and adds a dedicated CI job to ensure all unit tests are executed.
ESLint has been integrated across the workspace to enhance code quality. A new error ruleset ensures that any new linting errors introduced by a PR will now cause CI failures, while existing warnings are visible but non-blocking. This update introduces new `npm run lint`, `npm run lint:affected`, and `nx lint <project>` commands for developers.
Consolidated seven hand-copied Supabase database type definitions into a single, centrally generated file. This refactoring significantly improves the accuracy and completeness of database types by generating them directly from the production schema, addressing issues where previous copies were outdated or incomplete. A new tool was introduced to automate this generation process.
The display of overtime approval periods has been enhanced for both desktop and mobile. On desktop, 'Start OT' and 'End OT' are now combined into a clearer 'Work Period' column. Mobile approval cards now show more details, including work date, time range, hours, reference, and submitted time. Overtime dates are also formatted correctly, including periods spanning overnight.
The HR Leave Allocation feature now accurately includes legacy and cascade-resolved Ordinary Leave usage, providing a more comprehensive view of leave balances.
A new ID lookup API has been introduced within the Utopia Finance application, implemented as a Supabase function.
We've enhanced the process for deleting attendance records, making it safer and more user-friendly. When deleting, you'll now receive clear information about any linked claims or corrections, ensuring data integrity and providing better control over the deletion process.
Implemented a new backend API (`deleteHrAttendance`) and transactional RPC (`delete_hr_attendance_v1`) for HR attendance deletion. This ensures robust handling of foreign key constraints, proper cleanup of related corrections and audit trails, and improved error reporting for file deletions. Includes new database migrations.
HR Generalists can now safely delete attendance records with improved user feedback. The system provides clear warnings for linked Post OT claims and corrections, and allows adding a deletion reason for auditability.
Users can now select 'others' more reliably when setting times within the Shift Roster, improving flexibility for scheduling.
Introduced new database migrations for `profiles_work_schedule` to support dynamic shift roster days and hours based on work schedules. Added 'Flexi' work schedule option and updated backend logic for public holidays across HRMS, Personal, and Work spaces.
The Shift Roster feature now automatically populates days and hours based on your defined work schedule. A new 'Flexi' work schedule option has also been introduced, providing more flexibility in managing employee shifts.
Implemented paying bank capture for SPR, General/Benefit Claim, and Backcharge bank submissions. This involved backend API modifications, new database fields via migration `20260828130000_capture_paying_bank.sql`, and frontend UI components for bank selection and display in AP workflows. Comprehensive backend and Playwright tests were added.
Account staff can now select or enter the paying bank when submitting SPR, General/Benefit Claim, and Backcharge payments. This bank information is captured, stored, and displayed in submission details, activities, and batch history. The system suggests the paying company's configured bank, but custom values are also allowed.
Implemented a new server-authoritative workflow for cancelling approved supplier payment types. This involved significant updates to the finance backend API, services, and repositories, new frontend components for cancellation dialogs, and the addition of database migration `20260828120000`. The feature includes comprehensive backend and E2E test coverage.
AP and Finance Managers can now cancel approved, unsubmitted supplier payment types. This feature requires a mandatory reason for cancellation, preserves approval and payment history, and ensures cancelled items are excluded from all active processing queues and calculations.
We've added new capabilities for Accounts Payable Supplier Payments. You can now return individual payments to 'Pending Bank Submission' to manage receipts (replace or delete) while keeping your existing approvals and payment history intact.
Implemented Hub-style AP Supplier Payment actions, enabling return to Pending Bank Submission, receipt replacement/deletion, and approval preservation. Includes audit logging, storage cleanup, confirmation dialogs, and refreshed OpenAPI types. Resolved generated-schema merge conflict without endpoint loss. Added backend workflow and roll-up tests, and mocked Playwright coverage.
You can now return individual AP Supplier Payments to 'Pending Bank Submission' status. This allows you to replace or delete associated receipts while preserving existing approvals and workflow history.
Finance users can now easily trace bulk payments for claims and supplier payments with the introduction of unique Bulk IDs. This enhancement provides better visibility and management of multiple payment submissions.
The incident report staff search for Managers and Directors in the Work application has been refactored. The previous Business Unit → Department filtering was replaced with a Hub-style staff search, enabling discovery of active staff regardless of company, department, or role. Business unit authorization, hydration, and snapshot construction are now centralized in pure utilities. This update also includes a fix for responsive UI layout issues with long staff metadata.
Managers and Directors can now find active staff more easily when assigning reviewers in incident reports. The updated search allows you to discover staff regardless of their company, department, or role. The system also ensures that selected staff share at least one business unit with you, and the report's layout has been improved to better display long staff names.
Shared dialog components across all applications now implement a maximum height and vertical scrolling on mobile devices. This ensures that dialog content and action buttons remain fully visible and accessible, improving the user experience on smaller screens.
Implemented new features for Petty Cash including staff status calculation and a bad debt toggle. This involved adding new domain logic (`status-calculation.ts`), database migrations (`petty_cash_employee_status.sql`), and updates to `database.types.ts` across multiple applications.
HR Generalists can now view the status for each staff member in Petty Cash and manage bad debt using a new toggle button.
Users can now access a new Account Filing feature within the finance space. This allows you to view all account records and export them as PDFs, either individually or as a compiled document.
Managers can now benefit from improved filtering when reviewing attendance exceptions within the HRMS system, streamlining the management of employee attendance.
A new entry has been added to the production registry, documenting the merge SHA and successful production workflows for the attendance exception feature release.
Implemented a database migration to correctly filter the attendance exception queue for managers, ensuring only submitted or reviewed requests are displayed and excluding draft/cancelled entries. This addresses an edge case before genuine requests are entered in production.
Introduced a new manager-approved attendance exception workflow across Hub HRMS and Work Station, including new API endpoints, frontend pages, and database migrations ('20260825100000_attendance_exception_requests.sql'). This feature supports emergency partial-day and medical timeslip requests with evidence validation.
Employees can now submit attendance exception requests for emergency partial-day or medical timeslips, which are routed to their direct manager for approval. This new workflow ensures proper tracking and policy adherence for attendance adjustments.
New policies have been introduced for attendance exceptions: emergency partial day requires actual verified worked time, and medical timeslips allow paid approved missing scheduled windows with evidence.
Managers can now approve or deny attendance exception requests, such as emergency partial-day and medical timeslips, directly from their queue in Work Station.
HR Generalists can now manage manager-approved attendance exception requests, including emergency partial-day and medical timeslip requests, with new workflows in Hub HR.
The Post-OT fallback shipment, released via PR #359, has been officially recorded in the release history.
Implemented a manual fallback for Post OT Overtime Applications, including a database migration (`allow_post_ot_submission_fallback.sql`) to formalize existing RLS policies and check constraints. This change ensures data integrity by rejecting overlapping active requests and requiring manager approval. This release is a draft, pending further verification before full production rollout.
Post OT staff can now manually submit Overtime Applications if their automatic record is missing. The system will guide you to check your OT History first and prevent duplicate requests. This ensures all overtime is recorded accurately.
Resolved an issue where the selected currency type for supplier payments was not always correctly updated and stored in the database. This fix ensures that currency types are accurately reflected across the system, including the SPR tracker.
Seven new environment variables (`NEXT_PUBLIC_SCAFFOLDING_URL`, `NEXT_PUBLIC_IBNU_SINA_URL`, etc.) have been added to configure the URLs for the new business unit applications. These variables are crucial for linking the Sales workspace tiles to the correct application instances in different environments.
New `sales.<bu>.view` policies have been introduced for each of the 7 new business unit workspaces. Administrators can now grant or deny access to these individual business unit tiles via the Work → `/user-access` → Sales App interface.
Detailed guidance has been added for developers on how to integrate Single Sign-On (SSO) for new business unit applications. This includes patterns for Supabase-JS SPAs and apps with their own backend/HTTP-only cookies, leveraging the shared Supabase parent-domain cookie for seamless user experience.
The Sales workspace now includes 7 new business unit tiles: Scaffolding, Ibnu Sina, Sticker Lorry, Jom Vend, Kak Kenduri, RevMove, and Room Rental. Each tile provides direct access to its respective application, with seamless sign-in via shared cookies. Access to these tiles can be managed by administrators.
Users can now compile completed Supplier Payment Requests (SPR) with a new dedicated button. The copy button for SPRs has also been updated for improved usability within the Accounts Payable section.
Implemented multi-Business Unit (BU) support in the Operations Efficiency (OE) application. This feature introduces `BuAccessGuard` for backend access control and updates `OeAuthController`, `OeProxyController`, and various frontend components to manage BU context. A new `bu-oe-contract.md` document details the integration.
The Operations Efficiency application has been enhanced to support multiple Business Units (BUs). This update improves data segmentation and access control, ensuring users interact only with data relevant to their assigned Business Units.
The 'What's New' page within the Utopia Launcher now accurately reflects all recent updates, including the 'HR Generalist → Attendance Correction' entry, by ensuring its changelog data is fully synchronized.
Resolved an issue where `git stash` conflict markers were accidentally committed to the root `CHANGELOG.md` file, causing them to render verbatim. The file now displays cleanly.
HR Generalists can now monitor missed clock-out corrections across the organization. A new read-only Attendance Correction queue and detail view allow auditing of all such corrections.
Managers can now review and approve or reject employee requests for missed clock out attendance resubmission directly within the Work space. This new approval flow streamlines the process for correcting attendance records.
A new 'Contra with Last Claim' workflow for petty cash has been implemented, integrating across `utopia-hrms` and `utopia-finance` applications. This includes new API endpoints, database schema migrations (`petty_cash_contra_general_claims`), and UI components for managing pending claims and contra audits in various user spaces (Personal, Manager, Account).
Users can now manage petty cash contra claims with a new workflow integrated across HRMS and Finance. This streamlines the process for handling last claims and improves visibility.
The "Contra with Last Claim" feature for petty cash, previously live in production, has been reverted. This rollback was performed as a new, independent implementation (PR #349) is being adopted. Consequently, claims previously marked as 'Contra' may now show negative balances, and the 'Revert Bank Submission' action has been removed. Manual reconciliation will be required for affected claims once the new implementation ships.
A fix for petty cash contra entries has been deployed.
We've introduced a new 'Contra with Last Claim' feature for petty cash management. This enhancement allows HR to easily settle outstanding claims by contra-ing them against returns, ensuring accurate balances. Finance users also gain a new 'Revert Bank Submission' action for better claim reconciliation.
Introduced a new `finance_status='Contra'` for petty cash claims, ensuring accurate balance calculations across all applications. Implemented a new HR workflow for 'Contra with Last Claim' and a 'Revert Bank Submission' action for Finance, improving end-to-end claim settlement and audit trails. No schema changes were required.
Finance users will now see petty cash claims settled by HR via 'Contra with Last Claim' clearly marked with a new 'Contra' status. Additionally, a new 'Revert Bank Submission' action is available to reverse bank-submitted claims that were not processed, making them eligible for contra and improving claim reconciliation.
HR Generalists can now use a new 'Contra with Last Claim' method for petty cash returns. This process allows you to select open claims, automatically pre-filling the return amount, and marks the claims as 'Contra' to ensure accurate balance tracking and prevent negative on-hand balances.
A significant update has been deployed to refine the petty cash balance calculation logic across all applications. This involved a comprehensive review and correction of 'bucket rules' in 8 Supabase-backed applications, updating the `utopia-finance` backend and frontend to ensure consistent `balanceAtHand` computation, and standardizing the calculation across 27 UI components. Key technical changes include filtering out zero-value phantom entries, precise handling of `accountPending` and `financePending` statuses, and ensuring manager and finance approval stages are provably disjoint. This update ensures data consistency and accuracy across all petty cash interfaces.
We've rolled out an important update to ensure your petty cash balances are always accurate across all applications, including your Personal, Manager, and Finance portals. This fix standardizes how 'balance at hand' is calculated, correctly accounting for pending claims and removing any phantom entries, so you always see the most reliable figures.
Petty cash deletions now correctly update your ledger and balances, ensuring accurate financial records. Previously, deleting a petty cash entry might not have reflected correctly in your balance or the ledger. Additionally, summary cards for petty cash now refresh instantly to show the most up-to-date figures.
Resolved issue #335 by adding 'UTOPIA ACCELERATOR SDN BHD' to the hardcoded company list in 'apps/utopia-personal/src/shared/ui/components/ClaimFormV2.tsx', enabling employees to submit claims under this company.
Employees can now select 'UTOPIA ACCELERATOR SDN BHD' from the company dropdown when submitting General or Benefit claims in the Personal app.
The manager's leave approval workflow in the Utopia Work app has been refactored to remove the HR approval step. This involved updating `ManagerLeaveApprovalDetailPage.tsx` and `ManagerLeaveApprovals.tsx` to remove HR-related UI elements (columns, badges, filters) and logic. Global search/filter logic was adjusted, and confirmation messages were updated. Obsolete cascade approval logic and variables were also removed for code simplification.
The leave approval workflow for managers in the Utopia Work app has been streamlined. HR approval is no longer required after a manager's decision, making the manager's approval final. The user interface and messages have been updated to reflect this simpler process.
Deployed the new Ibnu Sina workspace, which involved a new database migration (`sales_ibnu_sina_grant`) and updates to user access registries across personal and work spaces to configure feature availability.
Users can now access the new Ibnu Sina workspace directly from the sales application, providing dedicated tools and features.
The Shift Roster feature has been updated to improve how draft changes are saved, preventing errors. You will also notice improved visibility for departments, and refined handling of draft working times for better assignment and custom time input.
Introduced significant improvements to the Leave History and Leave Details features in the Utopia Personal app. This includes grouping leave applications by category (General, Medical, Special), simplifying the manager approval flow by removing HR approval stages, and correcting the display of applicant names. Frontend logic, E2E, and unit tests were updated to reflect these changes, along with the addition of `LeaveApplicationCategory` type and `getLeaveApplicationCategory` utility.
We've enhanced the Leave History and Leave Details pages in the Personal app. You'll now see your leave applications grouped by categories like General, Medical, or Special Leave. The leave approval process has been simplified to a manager-only timeline, and applicant names are now displayed more accurately.
The Leave History and Leave Details pages in the Personal app have been improved. You can now view your leave applications grouped by categories such as General, Medical, or Special Leave. The approval process for leave requests has been simplified to a manager-only timeline, and applicant names are now displayed more accurately.
Recorded the merge SHA and production verification evidence for the Personal Hub SOCSO/SKBBK payslip split release.
Users will now see a correct breakdown of SOCSO and SKBBK contributions in their Hub payslips within Personal Space, resolving an issue where SKBBK was incorrectly grouped under SOCSO.
A new database index has been implemented to enhance the efficiency and stability of U-Money's supplier payment credit card reconciliation, particularly as transaction history expands.
Page titles across various Finance features, including Accounts Payable, Backcharge Verification, Claims SGS, Advance Salary, and Analytics, have been updated for clarity. Additionally, a fluid layout has been applied to these components for an improved user experience.
The invoice summary now includes a detailed list of invoices for bulk payments, showing the total amount and associated request IDs. Descriptions are now integrated directly within each invoice section for better clarity.
Implemented new functionality for managing CC recipients on supplier payments. This includes database schema updates, new API endpoints, and corresponding frontend components across the Finance, Personal, and Work applications. A new child table `supplier_payment_cc_recipient` was added.
Users can now manage CC recipients for supplier payments, allowing for better communication and tracking of payment-related notifications within the Finance, Personal, and Work spaces.
The Shift Roster feature now utilizes a new grant-based access system, enhancing control over who can view and manage shifts.
Users can now see pending leave requests directly within the Shift Roster, providing a more complete view of team availability.
The `DataTableToolbar` component in HRMS now supports a `hideReset` prop for custom clear/reset controls. New end-to-end tests have been added to verify filter wrapping and action alignment on benefit claims and leave approval pages.
The HRMS app now features enhanced table filter toolbars, particularly for benefit claims approval and leave approval pages. Filters now wrap neatly, display clearer selection badges, and the 'Save Filter' and 'Clear Filter' actions are better aligned for improved usability.
The leave application approval workflow has been refactored across `utopia-hrms`, `utopia-personal`, and `utopia-work` applications. HR-specific approval views and functions have been removed, standardizing approvals to be manager-only. This includes a new SQL migration.
A new SQL migration (`20260812110000_standardize_leave_manager_only_approval.sql`) has been added to standardize the leave approval process, ensuring it is manager-only. The `docs/database.md` file was also updated.
The HR Generalist space no longer includes views or functions for approving leave applications. This responsibility has been shifted entirely to managers to streamline the process.
The leave application approval process has been updated. HR approval steps have been removed, and all leave applications will now be approved solely by managers, simplifying the workflow for employees and managers.
Users can now reliably filter attendance records within the Operations Efficiency space, resolving a previous issue.
Implemented manual phone entry for CC recipients in the Supplier Payment Request (SPR) dialog. This involved changes to `SupplierPaymentCcRecipient` for `profileId: string | null`, deduplication logic in `utopia-work` and `utopia-finance` submit paths, and `SupplierPaymentController.normalizeCcRecipients` to handle `profileId`-null entries. Manual entries are stored in `supplier_payment_master.cc_recipients` and handled by the WhatsApp sender.
Staff using the Utopia Finance application can now manually add phone numbers for CC recipients in the Supplier Payment Request (SPR) dialog, even if the person doesn't have a Hub profile.
A fix has been applied to update the leave cascade application and tracker with a new calculation logic. This involved changes to `src/domains/leave/cascade.ts` and related API and frontend components within the `utopia-personal` application.
The leave cascade application and tracker have been updated with a new, more accurate calculation logic. This ensures that leave applications are processed correctly within your personal space.
Implemented features to enhance draft editing functionality within the Shift Roster module and improved user access visibility, affecting `ShiftRoster.tsx` and `UserAccess.tsx`.
This release brings significant enhancements to the Shift Roster, including improved draft editing, and better visibility for user access controls.
User access visibility has been improved, providing clearer insights into who has access to what features and data.
Shift Roster now offers enhanced draft editing capabilities, making it easier to manage and refine your shift schedules before publishing.
Introduced a new feature allowing CC recipients for Supplier Payment Request (SPR) applications. This involved updates to `utopia-finance` backend and frontend, `utopia-work` frontend, and new database migrations for `supplier_payment_cc_recipients`.
You can now add Carbon Copy (CC) recipients to your Supplier Payment Request applications, ensuring additional stakeholders receive notifications.
We've streamlined how environment variables are managed for local development. Now, a single `.env` file handles all configurations, making setup easier and more secure, especially for new team members. Existing users will need to run a simple migration script.
The environment configuration has been refactored from a two-file (`.env` + `.env.dev.local`) model to a single `.env` file. Project-specific keys are now prefixed (`PROD__`, `DEV__`) and selected via the `APP_ENV` variable, processed by `tools/env-switch.js`. This change impacts all applications and requires a migration step for existing checkouts.
Two new scripts, `tools/env-switch.js` and `tools/migrate-env.sh`, have been introduced to manage the new single-file `.env` setup. `env-switch.js` handles environment selection, and `migrate-env.sh` assists in converting old `.env` configurations.
Environment variables are now managed through a single `.env` file, using `PROD__` and `DEV__` prefixes. The `APP_ENV` variable selects the active environment, simplifying setup and enhancing security by preventing accidental exposure of production secrets.
Resolved an issue where `utopia-manager`, `utopia-director`, `utopia-supervisor`, and `utopia-launcher` applications failed to load data tables due to missing `use-persisted-filters` modules, resulting in 500 errors. The necessary module has been added to these applications, ensuring data tables load correctly.
To enhance the stability of production deployments, a new build gate has been added for all pull requests targeting the `main` branch. This ensures that all code is successfully compiled and passes essential quality checks *before* it can be merged, significantly reducing the risk of deploying broken applications to production environments.
A new GitHub Actions workflow (`pr.yml`) has been implemented for pull requests targeting the `main` branch. This workflow now performs `nx affected` builds and quality checks (import casing, brand verification) *before* code is merged. This ensures that code compiles correctly and passes basic quality gates, preventing broken changes from reaching `main` and subsequently production deployments. The workflow intelligently resolves affected build targets to accurately reflect changes.
Addressed mobile responsiveness issues across various approval detail pages (e.g., ManagerClaimDetails, ManagerBackchargeDetails) and the shared ApprovalSteps component. Changes span multiple applications including utopia-admin, utopia-director, utopia-finance, utopia-personal, and utopia-work, ensuring better UI adaptation on mobile screens for approval workflows.
We've improved the mobile responsiveness of approval pages throughout the system. Whether you're reviewing claims, backcharges, or supplier payments, you'll now experience a smoother and more consistent layout on your mobile device.
Missing files for `usePersistedFilters` were added to the Utopia HRMS and Operation Efficiency (OE) applications. This ensures that data table filters can be properly persisted and recalled within these applications.
We've rolled out an update that significantly improves the mobile responsiveness of various applications within your Personal Space, including Backcharge, Leave, Overtime, SGS Claims, and Supplier Payment. This ensures a smoother and more consistent experience when accessing these features on mobile devices.
This release enhances Shift Roster draft visibility and management features across the HRMS, Personal, and Work applications. Key changes include improved code structure for readability and maintainability, and a cleanup of the shift roster draft edit workflow.
Users can now more easily view and manage their Shift Roster drafts across HR, Personal, and Work spaces, with improved visibility and streamlined workflows.
The Utopia OE backend deployment workflow has been updated to trigger from the `main` branch. This change aligns OE's deployment process with other production applications, which now all deploy from the `main` branch, following the retirement of the `development` branch.
The `main` branch has been designated as the sole production trunk for the repository, retiring the `development` branch. All production deployments, including Utopia OE, now trigger exclusively from `main`. This change streamlines the CI/CD pipeline and consolidates all production releases onto a single branch. Note: A temporary gap in release gating exists, to be addressed by PR #288.
The `main` branch is now the default branch for the repository, replacing `development`. All new pull requests should target `main`. This change simplifies our development workflow by consolidating all active development and production releases onto a single branch.
This production release includes critical fixes for mobile responsiveness in Overtime Summary tables across various applications and addresses several issues within the Finance module, specifically related to Supplier Payment Request (SPR) tracking, compilation, and mobile display for Finance Launcher, Backcharge, and SPR applications.
Addressed issues in the Finance module, including improved mobile responsiveness for the Finance Launcher, Backcharge Application, and Supplier Payment Application. Fixed a bug where compiled Supplier Payment Requests (SPR) could merge with newly added ones, and resolved a 'bad request' error in the SPR tracker.
The Overtime Summary tables across various applications now display correctly on mobile devices, enhancing usability for managers and employees.
Job log and outcome cards in the Ops Efficiency space now prominently display the order number, making it easier to identify and track items at a glance.
This release includes a fix for Ordinary Leave allocations, implementing annual totals and updating related calculations in utopia-hrms. It also incorporates an update to the docs/database.md file. See PR #277 for details.
The database documentation has been updated. Please review for the latest information.
Ordinary Leave allocations now include annual totals and updated related calculations, providing more accurate leave management for HR Generalists.
Implemented an update to the Public Holiday usage deduction logic within the HRMS leave allocation domain. This includes modifications to `allocationApi.ts` and the introduction of new `benefit-usage.ts` and `benefit-usage.test.ts` files to refine calculations.
Public holidays are now accurately deducted from leave usage within the HR Generalist space's leave allocation feature, ensuring correct leave balances for employees.
This release brings several enhancements and fixes across the platform, including improved job notifications in Operation Efficiency, better Shift Roster management, decoupled HR Generalist access, and a more reliable leave application process.
This release promotes recent features and fixes from the development branch to production, including updates to Operation Efficiency, HR Management, Work, and Personal applications.
The leave application chooser is now enabled on all hosts within the Personal space, ensuring consistent access for all users.
The HR Generalist role has been decoupled from the main HR app tile, providing more flexible access and management.
The Shift Roster now has improved visibility for draft entries and the edit button, making it easier to manage your work schedules.
You can now directly open a job from a push notification in the Operation Efficiency app, streamlining your workflow.
Completed the August 3rd, 2026 release, which includes version updates for Utopia HRMS, Utopia Launcher, Utopia Personal, and Utopia Work applications, along with corresponding changelog updates.
Addressed a build issue for the Utopia Sales app on Vercel where `tsconfig.json` validation failed due to an undeclared `@types/node` dependency. This ensures successful builds and typechecking.
Synchronized `package-lock.json` to reflect updated package versions across several applications (Finance, HRMS, Launcher, Personal, Work) that were previously out of sync.
Integrated a new notification ingest endpoint with configurable properties. A production release was performed, including version bumps and changelog updates across applications.
Removed `nxCloudId` and set `neverConnectToCloud` in `nx.json` to resolve an issue where CI builds (e.g., on Vercel) would fail due to an unauthorized Nx Cloud workspace. Nx tasks now run locally in CI, maintaining local caching without requiring Nx Cloud connection.
Added a new developer-only entry point for the Wiki. This release also includes updates to the Caddyfile and a new deployment workflow for the Sales application, alongside other infrastructure improvements.
A routine release cut was performed for the 27th July 2026 release, involving version bumps and changelog updates across applications.
A new production release has been deployed, including version bumps and changelog updates across various applications. This release incorporates new features for personal pay documents and HR access controls, along with UI fixes.
Updated Cross-Origin Resource Sharing (CORS) configuration and improved error handling across the API, enhancing security and system stability.
Resolved an issue with the `ops_profiles` sync-trigger for improved data consistency.
Version 2.1.0 has been released across all active frontends, including new features and bug fixes. This release also includes the rollout of Playwright end-to-end testing for all active frontends and updates to internal documentation and changelogs.
Replybox webhooks now leverage Remote Procedure Calls (RPC) for enhanced processing efficiency and reliability. This update includes a new database migration to support the RPC-based webhook insertion.
Resolved an issue preventing `hr.utopiagroup.com.my` origin from accessing HRMS edge functions due to CORS policy.
Implemented a new GitHub Actions workflow to automatically sync wiki documentation upon pull request closure. This release also includes various backend and infrastructure improvements, such as database migrations, CORS configuration updates for HRMS, and general dependency bumps.
mainauto-posting releases from main, so every PR merged here is a production change. Each update also refreshes the Auto Posting pages when the change clearly belongs there.
mainauto-posting releases from main, so every PR merged here is a production change. Each update also refreshes the Auto Posting pages when the change clearly belongs there.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
mainutopia-bd-lead releases from main, so every PR merged here is a production change. Each update also refreshes the BD Lead pages when the change clearly belongs there.
mainutopia-bd-lead releases from main, so every PR merged here is a production change. Each update also refreshes the BD Lead pages when the change clearly belongs there.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
developmentutopiaspace-ops releases from development, so every PR merged here is a production change. Each update also refreshes the Ops App pages when the change clearly belongs there.
developmentutopiaspace-ops releases from development, so every PR merged here is a production change. Each update also refreshes the Ops App pages when the change clearly belongs there.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.
This source change was recorded, but automatic documentation classification was unavailable. Review the linked change before updating a feature page.