# Porting Bigbys Improvements to Smdummy, Then Solidmark Last updated: 2026-07-21 ## Objective The goal is to make the improved Bigbys application portable, prove the port in Smdummy, and only then upgrade Solidmark. The installations have different roles: | Installation | Role | Rule | |---|---|---| | Bigbys backup | Improved source code | Copy code and migrations, never its production records or secrets | | Smdummy | Experimental integration environment | Port, repair, migrate and test here first | | Solidmark | Current live production application | Do not modify until Smdummy passes the complete acceptance gate | The intended result is: ```text Bigbys application code and safeguards + Target database, brand, domain, secrets and uploads = Portable Smdummy or Solidmark installation ``` This is not a database replacement and not a folder rename. The target keeps its own company identity and operational records. ## Source and installation paths Use this backup as the source of truth: ```text C:\Users\HRIS-SERVER\Documents\Rabaya_FILES\BACKUP_BIGBYS(17-07-2026)\bigbys ``` Installations: ```text C:\xampp\htdocs\smdummy C:\xampp\htdocs\solidmark ``` Do not use the live `C:\xampp\htdocs\bigbys` directory as the permanent source. It can contain deployment-specific configuration or partial operational changes. ## How to run the commands in this tutorial Unless a section explicitly says otherwise, commands are run in a **normal Windows PowerShell window**. Do not run them in phpMyAdmin, Command Prompt (`cmd.exe`), Git Bash, the browser console, or a PHP file. Most filesystem and PHP commands use absolute paths and can be launched from any current directory. However, keep the same PowerShell window open because variables such as `$sourceRoot`, `$targetRoot`, `$stageRoot` and `$rollbackRoot` exist only in that window. Use this command-location map: | Command type | Where to run it | |---|---| | Path variables, Robocopy and file operations | Normal PowerShell, from any directory, in the same window | | `C:\xampp\php\php.exe ...` | Normal PowerShell, from any directory | | SQL statements | phpMyAdmin **SQL** tab after selecting the named test database | | Editing `backend/.env` or `frontend/.env` | A text editor such as VS Code or Notepad; never the PowerShell prompt | | `npm.cmd ci`, tests, lint and build | PowerShell after `Set-Location "$stageRoot\frontend"` | | Browser/manual checks | Browser pointed at the staging URL | | Apache stop/start | XAMPP Control Panel | When a command block contains variables beginning with `$`, do not open a new PowerShell window between the variable-definition step and that command. If you close the window, rerun the variable-definition block first. Before pasting a command, read the label immediately above it: - **Run from** identifies the program and directory. - **Requires** identifies earlier steps that must already be complete. - **Expected** describes a successful result. - **Stop if** describes a condition that must be resolved before continuing. Never paste the complete tutorial into PowerShell. Run one code block at a time, inspect its output, and continue only when it matches the expected result. # Part I — Experimental Smdummy Port ## 1. What comes from Bigbys Port the improved application code: - Authentication and session handling. - Credentialed CORS rules. - API guards, permissions and tenant isolation. - Database environment loader and migration runner. - Employees, departments and positions. - Attendance, biometrics and DTR. - Scheduling, shifts and break mappings. - Leave and overtime workflows. - Payroll, accounting and thirteenth-month features. - Dashboard and pending-count handling. - Shared frontend API clients and contexts. - Automated tests and quality-gate scripts. ## 2. What remains target-specific Preserve from Smdummy during the experiment and from Solidmark during production: - Database and all database records. - Company and brand rows. - Employees, users, attendance and payroll history. - Database credentials. - Authentication secret. - SMTP credentials. - Domain and allowed origins. - Uploads and generated files. - Logs. - Logos, colors and public branding. Never copy Bigbys production data or secrets into another tenant. ## 3. Files and directories not to overwrite Do not overlay these from Bigbys: ```text backend/.env frontend/.env backend/uploads/ backend/logss/ backend/cache/ backend/database/ backend/super backup databases/ backend/scratch/ frontend/node_modules/ frontend/dist/ frontend/dev-dist/ dist/ .git/ ``` Do not import: ```text backend/database/*.sql backend/super backup databases/*.sql ``` Review or merge these instead of blindly overwriting them: ```text .htaccess vercel.json frontend/vite.config.js frontend/src/authentication/LandingPage.jsx frontend/Styles/globalcolor.css frontend/public/systemImage/ frontend/public/manifest.json ``` Never transfer these values between installations: ```text AUTH_KEY DB_PASSWORD MAIL_PASSWORD DB_NAME CORS_ALLOWED_ORIGINS production URLs ``` ## 4. Export the Smdummy database **Run from:** A web browser at `http://localhost/phpmyadmin/`. **Requires:** MySQL is running in the XAMPP Control Panel and you know which database Smdummy currently uses. Before changing anything: 1. Open phpMyAdmin. 2. Select the Smdummy database. 3. Choose **Export**. 4. Choose **Custom**. 5. Select every table. 6. Use SQL format. 7. Include object creation and `DROP TABLE` statements for reliable restoration. 8. Save the file outside `htdocs` with a timestamp. Example: ```text smdummy_before_bigbys_port_20260721_120000.sql ``` Do not continue without a recoverable database export. ## 5. Define and validate the Smdummy paths **Run from:** A normal PowerShell window, from any directory. **Requires:** `C:\xampp\htdocs\smdummy` exists and the Bigbys backup path below exists. The current PowerShell directory does not matter because these are absolute paths. Keep this window open for the remaining Part I commands. ```powershell $portStamp = Get-Date -Format "yyyyMMdd_HHmmss" $sourceRoot = "C:\Users\HRIS-SERVER\Documents\Rabaya_FILES\BACKUP_BIGBYS(17-07-2026)\bigbys" $targetName = "smdummy" $targetRoot = "C:\xampp\htdocs\$targetName" $stageRoot = "C:\xampp\htdocs\${targetName}_port_stage_$portStamp" $rollbackRoot = "C:\xampp\htdocs\${targetName}_before_port_$portStamp" $resolvedSource = (Resolve-Path -LiteralPath $sourceRoot).Path $resolvedTarget = (Resolve-Path -LiteralPath $targetRoot).Path [pscustomobject]@{ Source = $resolvedSource Target = $resolvedTarget Stage = $stageRoot Rollback = $rollbackRoot } | Format-List if ($resolvedSource -eq $resolvedTarget) { throw "Source and target must be different directories." } if (Test-Path -LiteralPath $stageRoot) { throw "Staging directory already exists: $stageRoot" } if (Test-Path -LiteralPath $rollbackRoot) { throw "Rollback directory already exists: $rollbackRoot" } ``` Stop if the displayed paths are not exactly what you expect. **Expected:** Four absolute paths are printed. `Source` ends in the backup `\bigbys`, `Target` is `C:\xampp\htdocs\smdummy`, and the Stage and Rollback directories do not exist yet. **Stop if:** A path is blank, points to Solidmark, or points outside `C:\xampp\htdocs` unexpectedly. ## 6. Create rollback and staging copies **Run from:** The same PowerShell window used in section 5, from any directory. **Requires:** `$targetRoot`, `$stageRoot` and `$rollbackRoot` are defined. The Smdummy database export is complete. **Live impact:** Read-only access to the current Smdummy files. Solidmark is not involved. Do not use `Copy-Item -Recurse` on the complete application. Protected `.git` objects can fail, and copying into an existing destination can create an unwanted nested `smdummy` directory. Create empty destinations: ```powershell New-Item -ItemType Directory -Path $rollbackRoot | Out-Null New-Item -ItemType Directory -Path $stageRoot | Out-Null ``` Create the rollback copy: ```powershell robocopy $targetRoot $rollbackRoot /E /R:2 /W:1 ` /XD .git node_modules dist dev-dist if ($LASTEXITCODE -ge 8) { throw "Rollback copy failed with Robocopy exit code $LASTEXITCODE" } ``` Create the staging copy: ```powershell robocopy $targetRoot $stageRoot /E /R:2 /W:1 ` /XD .git node_modules dist dev-dist if ($LASTEXITCODE -ge 8) { throw "Staging copy failed with Robocopy exit code $LASTEXITCODE" } ``` Robocopy exit codes `0` through `7` are successful or informational. Codes `8` and higher are failures. Never use `/MIR`, `/PURGE` or `/MOVE` for this port. **Expected:** Robocopy completes with an exit code from `0` through `7`. Both `$stageRoot` and `$rollbackRoot` contain `backend` and `frontend` directly. There must not be a nested path such as `$stageRoot\smdummy\backend`. Verify the layout: ```powershell Get-Item -LiteralPath ` "$stageRoot\backend", ` "$stageRoot\frontend", ` "$rollbackRoot\backend", ` "$rollbackRoot\frontend" | Select-Object FullName ``` **Stop if:** Access is denied, Robocopy returns `8` or higher, or a nested `smdummy` directory was created. If a failed attempt already created the staging directory, move it aside instead of copying into it again: ```powershell $partialStamp = Get-Date -Format "yyyyMMdd_HHmmss" if (Test-Path -LiteralPath $stageRoot) { Move-Item -LiteralPath $stageRoot ` -Destination "${stageRoot}_partial_$partialStamp" } ``` Then create a new empty `$stageRoot` and rerun Robocopy. ## 7. Overlay the Bigbys backend into Smdummy staging **Run from:** The same PowerShell window, from any directory. **Requires:** Section 6 completed successfully and `$stageRoot\backend` exists. **Live impact:** Only the experimental staging directory is changed. Live Smdummy and Solidmark remain unchanged. ```powershell robocopy "$sourceRoot\backend" "$stageRoot\backend" /E /R:2 /W:1 ` /XD uploads logss cache database "super backup databases" scratch ` /XF .env if ($LASTEXITCODE -ge 8) { throw "Backend overlay failed with Robocopy exit code $LASTEXITCODE" } ``` This is an overlay: - Matching application files are upgraded. - Missing Bigbys files are added. - Target runtime data is preserved. - Target-only files are not automatically deleted. **Expected:** Robocopy returns `0` through `7`. The staging backend now contains `server\env.php`, `server\admin_request.php`, `server\migration_runner.php`, `migrations`, and `tests`. Verify: ```powershell Get-Item -LiteralPath ` "$stageRoot\backend\server\env.php", ` "$stageRoot\backend\server\admin_request.php", ` "$stageRoot\backend\server\migration_runner.php", ` "$stageRoot\backend\bin\migrate.php" ``` ## 8. Backend foundation files These files are interdependent and must remain from the same Bigbys version: ```text backend/server/env.php backend/server/db_config.php backend/server/connection.php backend/server/cors.php backend/server/auth_helper.php backend/server/security_provider.php backend/server/rate_limiter.php backend/server/api_output_guard.php backend/server/authenticated_request.php backend/server/admin_request.php backend/server/sanitize_input.php backend/server/mailer_config.php backend/server/upload_config.php backend/server/migration_runner.php backend/server/retired_endpoint.php backend/config/brand_context.php backend/login.php backend/logout.php backend/ping.php backend/bin/migrate.php backend/scripts/migrate.php backend/migrations/ backend/tests/ ``` Do not combine an old `auth_helper.php` with a new `login.php`, or an old `connection.php` with the new environment loader. Port complete backend feature directories rather than isolated endpoints. This includes attendance, employees, mobile, overtime, payroll, scheduling, thirteenth month, departments, positions, branches, company configuration, users, permissions, work-time-break, work-time and work-week modules. ## 9. Quarantine experimental diagnostic endpoints **Run from:** The same PowerShell window, from any directory. **Requires:** The backend overlay is complete. **Live impact:** Only staging files are moved; nothing is deleted. Smdummy can contain target-only diagnostics: ```text backend/test_count.php backend/test_count2.php backend/optimize_biometrics.php ``` Move them outside the staged web root until they are reviewed: ```powershell $quarantineRoot = Join-Path $stageRoot "quarantine" New-Item -ItemType Directory -Path $quarantineRoot -Force | Out-Null foreach ($relativePath in @( "backend\test_count.php", "backend\test_count2.php", "backend\optimize_biometrics.php" )) { $candidate = Join-Path $stageRoot $relativePath if (Test-Path -LiteralPath $candidate) { Move-Item -LiteralPath $candidate -Destination $quarantineRoot } } ``` This is recoverable because the files remain in quarantine and in `$rollbackRoot`. ## 10. Create the Smdummy backend environment **Run the Copy-Item command from:** The same PowerShell window, from any directory. **Then edit:** The exact file shown by this command: ```powershell $backendEnvPath = "$stageRoot\backend\.env" $backendEnvPath notepad.exe $backendEnvPath ``` You may replace `notepad.exe` with VS Code. Do not edit `C:\xampp\htdocs\solidmark\backend\.env` during Part I. Create an environment file from the portable example: ```powershell Copy-Item -LiteralPath "$stageRoot\backend\.env.example" ` -Destination "$stageRoot\backend\.env" ``` Use a cloned database during the experiment: ```env APP_ENV=production APP_URL=http://localhost/smdummy_port_stage_TIMESTAMP APP_TIMEZONE=Asia/Manila APP_DEBUG=false DB_HOST=localhost DB_PORT=3306 DB_NAME=smdummy_port_test DB_USER=root DB_PASSWORD= AUTH_KEY=replace_with_a_unique_random_secret AUTH_TOKEN_TTL=86400 AUTH_LEGACY_TOKEN_UNTIL= MIGRATION_DEFAULT_BRAND_CODE=SMDUMMY CORS_ALLOWED_ORIGINS=http://localhost:5175 CORS_ALLOW_LOCALHOST=true LOG_PATH=logss/application.log AUTH_LOG_PATH=logss/auth_debug.log MAIL_HOST=smtp.gmail.com MAIL_PORT=587 MAIL_ENCRYPTION=tls MAIL_SMTP_AUTH=true MAIL_USERNAME= MAIL_PASSWORD= MAIL_FROM_ADDRESS= MAIL_FROM_NAME="Smdummy HRIS" UPLOAD_IMAGE_DIR=../dist/images UPLOAD_IMAGE_BASE_URL=http://localhost/smdummy_port_stage_TIMESTAMP/dist/images UPLOAD_LEAVE_DIR=uploads/leave_attachments UPLOAD_LEAVE_BASE_URL=http://localhost/smdummy_port_stage_TIMESTAMP/backend/uploads/leave_attachments UPLOAD_BIOMETRICS_DIR=uploads/biometrics UPLOAD_BIOMETRICS_BASE_URL=http://localhost/smdummy_port_stage_TIMESTAMP/backend/uploads/biometrics UPLOAD_MAX_BYTES=10485760 PAYROLL_DEFAULT_DIVISOR=26 PAYROLL_DEFAULT_HOURS_PER_DAY=8 ``` Replace `TIMESTAMP` with the actual staging folder suffix. Generate a unique key: ```powershell C:\xampp\php\php.exe -r "echo bin2hex(random_bytes(32)), PHP_EOL;" ``` Do not reuse the Bigbys or Solidmark `AUTH_KEY`. **Expected:** `$stageRoot\backend\.env` exists, `DB_NAME` ends in `_test`, and every URL contains the real staging folder rather than the word `TIMESTAMP`. Check non-secret settings without displaying passwords: ```powershell Select-String -LiteralPath "$stageRoot\backend\.env" ` -Pattern "^(APP_URL|DB_NAME|MIGRATION_DEFAULT_BRAND_CODE|CORS_ALLOWED_ORIGINS)=" ``` **Stop if:** `DB_NAME` points to live Smdummy or Solidmark, `AUTH_KEY` still contains `replace_`, or a URL still contains `TIMESTAMP`. ## 11. Create the Smdummy test database **Run from:** phpMyAdmin in a browser at `http://localhost/phpmyadmin/`. **Requires:** The Smdummy export from section 4. In phpMyAdmin: 1. Create `smdummy_port_test`. 2. Import the Smdummy database export into it. 3. Confirm all target tables and records were imported. 4. Confirm the staging `.env` points to `smdummy_port_test`. The test database name must end in `_test`. Never point the integration test harness at Solidmark or another production database. **Expected:** phpMyAdmin shows `smdummy_port_test` with the same operational tables and copied records as the experimental Smdummy database. ## 12. Verify target company and brand data **Run from:** The phpMyAdmin **SQL** tab after selecting `smdummy_port_test` in the left sidebar. Run: ```sql SELECT c.company_id, c.company_code, c.company_name, c.is_active AS company_active, b.brand_id, b.brand_code, b.brand_name, b.is_active AS brand_active FROM companies c JOIN brands b ON b.company_id = c.company_id ORDER BY c.company_id, b.brand_id; ``` Set `MIGRATION_DEFAULT_BRAND_CODE` to an active Smdummy brand returned by this query. Do not use a Bigbys or Solidmark brand code. Stop if valid company and brand records do not exist. Repair tenant records before applying tenant-scoping migrations. ## 13. Run ordered migrations on the test database **Run from:** The same PowerShell window used for the staging variables, from any directory. **Requires:** `$stageRoot\backend\.env` points to `smdummy_port_test`, and section 12 identified the correct active Smdummy brand code. ```powershell C:\xampp\php\php.exe "$stageRoot\backend\bin\migrate.php" ``` The migrations create the `schema_migrations` ledger and upgrade: 1. Department and position tenant scope. 2. Database-driven permissions. 3. Role-permission seeds. 4. Overtime identifiers. 5. Thirteenth-month deductions. 6. Sensitive-operation permissions. 7. Employee-related indexes. 8. API safeguard permissions. 9. Password-reset expiration. 10. Remaining protected route permissions. Verify in phpMyAdmin: ```sql SELECT migration, checksum, batch, execution_ms, applied_at FROM schema_migrations ORDER BY migration; ``` Do not edit an applied migration. Do not use `--repair-checksums` during a normal port. **Expected:** The command prints a migration batch and `[applied]` or `[skipped]` for every migration. An already applied migration being skipped is normal. **Stop if:** The output mentions the Solidmark database, duplicate/invalid tenant data, a checksum mismatch, or any migration failure. ## 14. Overlay the Bigbys frontend **Run from:** The same PowerShell window, from any directory. **Requires:** The backend overlay and test-database migration succeeded. **Live impact:** Only `$stageRoot\frontend` is changed. ```powershell foreach ($folder in @("src", "Styles", "tests", "scripts")) { $from = Join-Path "$sourceRoot\frontend" $folder $to = Join-Path "$stageRoot\frontend" $folder if (Test-Path -LiteralPath $from) { robocopy $from $to /E /R:2 /W:1 if ($LASTEXITCODE -ge 8) { throw "Frontend copy failed for $folder with exit code $LASTEXITCODE" } } } ``` Copy build and dependency contracts: ```powershell foreach ($file in @( "package.json", "package-lock.json", "eslint.config.js", "tailwind.config.js", "index.html", ".env.example", ".gitignore" )) { Copy-Item -LiteralPath "$sourceRoot\frontend\$file" ` -Destination "$stageRoot\frontend\$file" -Force } ``` Do not copy `node_modules`, `dist`, `dev-dist` or the Bigbys frontend `.env`. **Expected:** The staging frontend contains the Bigbys application shell, contexts, authentication screens, shared clients and tests, while generated dependency/build directories remain absent. ## 15. Keep the frontend shell compatible Keep these files from the same Bigbys version: ```text frontend/src/App.jsx frontend/src/main.jsx frontend/src/context/SessionContext.jsx frontend/src/context/PendingCountsContext.jsx frontend/src/components/utils/axiosInstance.js frontend/src/components/utils/apiFetch.js frontend/src/components/utils/authSession.js frontend/src/components/utils/AuthWatcher.jsx frontend/src/components/utils/IdleTimer.jsx frontend/src/components/utils/secureStorage.js frontend/src/authentication/ProtectedRoute.jsx frontend/src/authentication/RoleBaseRedirect.jsx frontend/src/authentication/useRoles.jsx frontend/src/authentication/login.jsx frontend/src/authentication/ForgotPassword.jsx frontend/src/authentication/ResetPassword.jsx frontend/src/components/navigation/Layou.jsx frontend/src/components/navigation/Logoutt.jsx frontend/src/components/navigation/menuAccessCache.js frontend/src/components/navigation/mobileAdminNav.jsx frontend/src/components/sidebar.jsx ``` Do not restore an old target `App.jsx` after copying the new contexts. The new application root must mount `PendingCountsProvider`, session routing and the idle timer. If Smdummy has a unique route, compare its original `App.jsx` from `$rollbackRoot` and deliberately re-add that route without removing the Bigbys providers. ## 16. Merge Vite configuration **Run from:** A text editor. Compare these two files side by side: ```text Bigbys source: \frontend\vite.config.js Smdummy stage: \frontend\vite.config.js ``` To open the staging file in Notepad from the same PowerShell window: ```powershell notepad.exe "$stageRoot\frontend\vite.config.js" ``` Do not run JavaScript from this section in PowerShell; it is configuration content to merge into `vite.config.js`. Do not blindly copy Bigbys `frontend/vite.config.js`; it contains deployment-specific proxy and allowed-host values. The merged target file must contain: - The target development hosts and proxies. - Build-version generation. - PWA cache cleanup. - `@backend`, `@api` and `@fetch` aliases. Required aliases: ```js resolve: { alias: { "@backend": resolve(__dirname, "../backend"), "@api": resolve(__dirname, "src/components/utils/axiosInstance.js"), "@fetch": resolve(__dirname, "src/components/utils/apiFetch.js"), }, }, ``` Do not carry Bigbys Cloudflare hosts or the `hris.centraljuan.com` development proxy into Smdummy unless intentionally used. ## 17. Create the Smdummy frontend environment **Run the Copy-Item command from:** The same PowerShell window, from any directory. **Then edit:** `$stageRoot\frontend\.env` in a text editor: ```powershell notepad.exe "$stageRoot\frontend\.env" ``` ```powershell Copy-Item -LiteralPath "$stageRoot\frontend\.env.example" ` -Destination "$stageRoot\frontend\.env" ``` Configure: ```env VITE_API_BASE_URL=http://localhost/smdummy_port_stage_TIMESTAMP/backend VITE_COMPANY_CODE= VITE_DEFAULT_BRAND_CODE=SMDUMMY VITE_DOMAIN_BRAND_MAP= VITE_REQUEST_BADGE_SYNC_MS=30000 VITE_REQUESTS_SYNC_MS=30000 VITE_REFRESH_INTERVAL=30000 VITE_MENU_ACCESS_CACHE_TTL_MS=30000 VITE_PERMISSIONS_CACHE_TTL_MS=30000 ``` Replace `TIMESTAMP` with the actual folder suffix. Rebuild after changing any `VITE_` value. **Expected:** `VITE_API_BASE_URL` points to the staging backend and never to `/bigbys/backend` or `/solidmark/backend` during Part I. ## 18. Preserve and review branding **Run the search command from:** The same PowerShell window, from any directory. `rg` must be installed; if it is unavailable, use the editor's global search. **Edit results in:** A text editor, one reviewed occurrence at a time. Do not run bulk search-and-replace across SQL or migration files. Review instead of blindly replacing: ```text frontend/src/authentication/LandingPage.jsx frontend/Styles/globalcolor.css frontend/public/systemImage/ frontend/public/manifest.json ``` Search for hardcoded brand and deployment values: ```powershell rg -n -i "bigbys|solidmark|smdummy|rakiyata|rabaya|centraljuan" ` "$stageRoot\frontend\src" ` "$stageRoot\frontend\Styles" ` "$stageRoot\frontend\public" ` "$stageRoot\backend" ` -g "!database/**" ` -g "!super backup databases/**" ` -g "!logss/**" ``` Change user-facing brands and deployment URLs. Do not rename migrations or modify historical dumps; those dumps should not be deployed. Prefer `.env` and database brand records over new hardcoded tenant names. ## 19. Rewrite rules **Run the Copy-Item command from:** The same PowerShell window, from any directory. **Then review:** `$stageRoot\.htaccess` in a text editor. The Apache configuration is not executed in PowerShell. The Bigbys root `.htaccess` is a path-neutral baseline for `/api` and `/backend/api` routes: ```powershell Copy-Item -LiteralPath "$sourceRoot\.htaccess" ` -Destination "$stageRoot\.htaccess" -Force ``` It must forward authorization headers: ```apache SetEnvIf Authorization "(.*)" HTTP_AUTHORIZATION=$1 ``` Review the result under the actual Smdummy path. Do not keep a rule that accidentally maps `/smdummy/api` to the Apache document-root `/backend` directory. Do not automatically copy `vercel.json`. ## 20. Install and statically verify **Run from:** The same PowerShell window. **Requires:** The frontend `.env` and merged `vite.config.js` are complete. Node.js is installed. The first command deliberately changes the current directory to the staging frontend. Run all subsequent `npm.cmd` commands in that directory: Install dependencies cleanly: ```powershell Set-Location -LiteralPath "$stageRoot\frontend" npm.cmd ci ``` PHP lint: ```powershell $phpFiles = Get-ChildItem "$stageRoot\backend" -Recurse -Filter *.php -File foreach ($file in $phpFiles) { & C:\xampp\php\php.exe -l $file.FullName | Out-Null if ($LASTEXITCODE -ne 0) { throw "PHP lint failed: $($file.FullName)" } } ``` Backend unit tests: ```powershell & C:\xampp\php\php.exe "$stageRoot\backend\tests\run.php" if ($LASTEXITCODE -ne 0) { throw "Backend tests failed." } ``` Frontend checks: ```powershell Set-Location -LiteralPath "$stageRoot\frontend" npm.cmd test if ($LASTEXITCODE -ne 0) { throw "Frontend tests failed." } npm.cmd run lint -- --quiet if ($LASTEXITCODE -ne 0) { throw "ESLint failed." } npm.cmd run build if ($LASTEXITCODE -ne 0) { throw "Production build failed." } ``` Missing imports, syntax errors and unresolved modules must be fixed. Large-chunk and old-Browserslist warnings do not by themselves fail the port. **Expected:** `npm.cmd ci` completes, PHP lint reports no syntax errors, backend tests pass, frontend tests pass, ESLint exits successfully, and Vite produces `$stageRoot\frontend\dist`. **Stop if:** An import cannot be resolved, a PHP fatal/syntax error appears, any test fails, or Vite exits with a nonzero code. ## 21. Database and HTTP tests **Run from:** The same PowerShell window, from any directory. The commands use absolute paths. **Requires:** MySQL is running, `smdummy_port_test` exists, migrations succeeded, and `$stageRoot\backend\.env` is configured. ```powershell $env:TEST_DB_NAME = "smdummy_port_test" $env:ENV_FILE = "$stageRoot\backend\.env" & C:\xampp\php\php.exe "$stageRoot\backend\tests\database.php" if ($LASTEXITCODE -ne 0) { throw "Database tests failed." } node "$stageRoot\backend\tests\http-smoke.mjs" if ($LASTEXITCODE -ne 0) { throw "HTTP smoke tests failed." } Remove-Item Env:TEST_DB_NAME -ErrorAction SilentlyContinue Remove-Item Env:ENV_FILE -ErrorAction SilentlyContinue ``` The tests must only use a database ending in `_test`. **Expected:** Database checks confirm required tables, columns, indexes and migration checksums. HTTP checks confirm explicit credentialed CORS, anonymous rejection and authenticated tenant isolation. **Stop if:** The printed database name does not end in `_test` or any fixture appears in a production database. ## 22. Manual Smdummy acceptance checklist **Run from:** A browser pointed at the Smdummy staging frontend. Start the staging Vite server from `$stageRoot\frontend` only if needed: ```powershell Set-Location -LiteralPath "$stageRoot\frontend" npm.cmd run dev -- --port 5176 ``` Keep the existing live application port separate. The example uses port `5176` to avoid replacing another Vite server on `5175`. Open the URL printed by Vite, normally `http://localhost:5176`. **Requires:** Apache and MySQL are running. The staging frontend `.env` points to the staging backend. Do not consider the experimental port successful until all of these work against the cloned Smdummy database: ### Authentication - Correct login succeeds. - Incorrect login fails safely. - Logout invalidates the session. - Refresh preserves a valid session. - Forgot Password sends a reset code. - Reset Password accepts a valid unexpired code. - Idle timeout works. ### Dashboard and navigation - Dashboard renders on desktop. - Dashboard renders below 768 pixels. - Pending counts load. - Roles and menu access load. - No React provider errors appear. - Navigation respects permissions. ### Employees and organization - Create and edit an employee. - Assign company, brand, department and position. - Archive or deactivate an employee. - Create and update departments and positions. - Cross-brand employee access is rejected. ### Attendance and scheduling - Import biometrics. - Load and edit attendance. - Verify DTR calculations. - Verify day and overnight shifts. - Load shifts and break settings. - Create and update schedules. - Submit, approve and reject schedule changes. ### Requests and payroll - Submit and approve overtime. - Submit and approve leave. - Pending badges update. - Generate payroll preview. - Verify allowances and deductions. - Finalize and void a test payroll batch. - Verify journal entries. - Verify thirteenth-month deductions. - Unauthorized roles cannot perform sensitive operations. ### Runtime services - Employee image upload works. - Leave attachment upload works. - Generated URLs use the Smdummy host. - SMTP authentication succeeds. - Logs are written to the configured target path. - APIs return JSON rather than PHP warnings or HTML fatal errors. - Browser console contains no CORS errors. ## 23. Smdummy acceptance gate **Decision point:** This section does not contain a deployment command. Record pass/fail evidence for every item. Solidmark remains untouched if even one critical item fails. Smdummy is considered a successful experiment only when: 1. All PHP files pass syntax checks. 2. Backend unit tests pass. 3. Frontend tests pass. 4. Security-contract tests pass. 5. ESLint passes. 6. The Vite production build passes. 7. All migrations apply to the cloned Smdummy database. 8. Database integration tests pass. 9. Authenticated HTTP and CORS tests pass. 10. Every critical manual operation above passes. 11. No Bigbys production data or secrets exist in Smdummy. 12. No Smdummy request accidentally targets `/bigbys/backend`. Do not touch Solidmark until this gate passes. The Smdummy experiment does not need to replace Solidmark or become publicly available. Its purpose is to reveal portability problems safely. # Part II — Controlled Solidmark Production Port **Production warning:** Do not run any Part II command merely because Part I files copied successfully. Part II begins only after the Smdummy acceptance gate is documented as passing. ## 24. Start a completely new Solidmark cycle **Run from:** A new normal PowerShell window opened specifically for the Solidmark cycle, from any directory. Do not reuse the Smdummy variables. The following block intentionally replaces them with Solidmark paths. After Smdummy passes, do not rename Smdummy to Solidmark and do not copy the Smdummy database or `.env`. Create a new set of variables: ```powershell $productionStamp = Get-Date -Format "yyyyMMdd_HHmmss" $sourceRoot = "C:\Users\HRIS-SERVER\Documents\Rabaya_FILES\BACKUP_BIGBYS(17-07-2026)\bigbys" $targetName = "solidmark" $targetRoot = "C:\xampp\htdocs\solidmark" $stageRoot = "C:\xampp\htdocs\solidmark_port_stage_$productionStamp" $rollbackRoot = "C:\xampp\htdocs\solidmark_before_port_$productionStamp" ``` Use the same tested Bigbys source plus any code fixes discovered during the Smdummy experiment. Those fixes must first be added back to the Bigbys source-of-truth backup and must pass the Bigbys/Smdummy quality gate. ## 25. Protect Solidmark before any change **Run database export from:** phpMyAdmin in the browser. **Run filesystem staging commands from:** The Solidmark PowerShell window created in section 24. **Live impact:** Read-only copying until the later migration and cutover sections. Do not stop or rename live Solidmark here. Because Solidmark is live: 1. Schedule a maintenance window. 2. Export the current Solidmark database immediately before work. 3. Create a filesystem rollback copy excluding only `.git`, dependencies and generated builds. 4. Create a separate Solidmark staging directory. 5. Clone the Solidmark database into a name ending in `_test`. 6. Keep the live `C:\xampp\htdocs\solidmark` directory unchanged throughout staging. Repeat the Robocopy staging process from Part I with `solidmark` paths. ## 26. Solidmark-specific configuration **Edit only these staged files:** ```text \backend\.env \frontend\.env \frontend\vite.config.js ``` Do not edit the live `C:\xampp\htdocs\solidmark` environment during staging. Create new Solidmark `.env` files. Do not copy the Smdummy or Bigbys `.env`. Solidmark must have its own: ```text DB_NAME and DB_PASSWORD AUTH_KEY APP_URL CORS_ALLOWED_ORIGINS MAIL_USERNAME and MAIL_PASSWORD MAIL_FROM_ADDRESS UPLOAD base URLs VITE_API_BASE_URL VITE_DEFAULT_BRAND_CODE VITE_DOMAIN_BRAND_MAP ``` Use Solidmark's company and brand records. The current Solidmark backend is missing the complete `positions` module, so ensure the Bigbys `backend/positions` directory and its migrations are included. ## 27. Repeat every test with Solidmark data **Run from:** The Solidmark staging paths using the same command locations described in sections 20–22. Replace `smdummy_port_test` with a cloned database name ending in `_test`, such as `solidmark_port_test`. Passing Smdummy proves portability but does not prove compatibility with the Solidmark schema or records. Repeat: - Migration tests against a cloned Solidmark database. - Backend and frontend automated tests. - CORS and authenticated HTTP tests. - Login and session tests. - Employee, attendance and schedule operations. - Leave and overtime workflows. - Payroll preview, finalization and voiding. - Upload and SMTP tests. - Desktop and mobile dashboard tests. - Tenant and permission isolation tests. Do not migrate the live Solidmark database until the Solidmark staging clone passes. ## 28. Solidmark production database migration **Run from:** The Solidmark PowerShell window, from any directory, during the approved maintenance window. **Requires:** A fresh production database export, stopped business writes, a completely passing Solidmark staging clone, and explicit confirmation that `$stageRoot\backend\.env` now names the production Solidmark database. **This is the first Part II step that changes the production database.** Immediately before production migration: 1. Export the Solidmark production database again. 2. Put Solidmark into maintenance mode. 3. Stop writes from attendance devices, imports and payroll operations. 4. Confirm the Solidmark staging `.env` contains the production Solidmark database and brand code. 5. Run the ordered migration runner once. ```powershell C:\xampp\php\php.exe "$stageRoot\backend\bin\migrate.php" ``` Inspect: ```sql SELECT migration, checksum, batch, execution_ms, applied_at FROM schema_migrations ORDER BY migration; ``` Running the migration command a second time should skip already applied migrations. **Stop if:** The configured database name is not the expected production Solidmark database or the migration runner reports any error. ## 29. Solidmark cutover **Run from:** The Solidmark PowerShell window, from any directory. **Requires:** Apache is stopped using the XAMPP Control Panel, the production migration succeeded, `$rollbackRoot` exists, and the final build passed. **This changes the live filesystem. Read every resolved path before running the rename commands.** Before cutover: - Confirm the rollback directory exists. - Confirm the latest database export exists outside `htdocs`. - Stop the Solidmark Vite server if it is running. - Stop Apache through the XAMPP Control Panel. - Confirm the stage and live paths resolve under `C:\xampp\htdocs`. Perform a recoverable directory swap: ```powershell $cutoverOldRoot = "C:\xampp\htdocs\solidmark_cutover_old_$productionStamp" if ((Resolve-Path -LiteralPath $targetRoot).Path -notlike "C:\xampp\htdocs\*") { throw "Unexpected Solidmark target path." } if ((Resolve-Path -LiteralPath $stageRoot).Path -notlike "C:\xampp\htdocs\*") { throw "Unexpected Solidmark staging path." } if (Test-Path -LiteralPath $cutoverOldRoot) { throw "Cutover backup already exists." } Rename-Item -LiteralPath $targetRoot ` -NewName (Split-Path $cutoverOldRoot -Leaf) Rename-Item -LiteralPath $stageRoot -NewName "solidmark" ``` Restart Apache and perform immediate checks before ending maintenance mode. **Expected:** `C:\xampp\htdocs\solidmark` is the tested staged application and `$cutoverOldRoot` contains the immediately previous live application. ## 30. Immediate Solidmark checks Confirm: 1. Login page and branding are Solidmark. 2. Browser requests target `/solidmark/backend`. 3. Login succeeds. 4. Dashboard renders on desktop and mobile. 5. Pending counts, roles and menu access load. 6. Employee lists are tenant-scoped. 7. Shifts and break endpoints return JSON. 8. No CORS errors appear. 9. SMTP authenticates with the Solidmark sender. 10. Upload URLs use the Solidmark domain. 11. Payroll and attendance read-only verification matches pre-port totals. Hard-refresh with `Ctrl+Shift+R`. Clear site data once if a stale PWA worker serves an old application shell. ## 31. Solidmark rollback **Run from:** A PowerShell window with the Solidmark variables redefined, while Apache is stopped. **Run only if:** A critical production operation failed and rollback has been authorized. Rollback immediately if login, tenant isolation, employee operations, attendance, payroll or uploads fail materially. Stop Apache, then: ```powershell $failedRoot = "C:\xampp\htdocs\solidmark_failed_port_$productionStamp" if (Test-Path -LiteralPath $failedRoot) { throw "Failed-port holding directory already exists." } Rename-Item -LiteralPath $targetRoot ` -NewName (Split-Path $failedRoot -Leaf) Rename-Item -LiteralPath $cutoverOldRoot -NewName "solidmark" ``` If the schema migration must also be reversed, restore the pre-port Solidmark database export through phpMyAdmin. Do not manually drop new columns or permission tables in production without a reviewed rollback script. Restart Apache and verify the restored application. ## 32. Retention Keep these until the upgraded Solidmark completes at least one real payroll cycle: ```text Solidmark filesystem rollback Solidmark cutover-old directory pre-port database exports Solidmark cloned test database Smdummy experimental installation deployment and verification logs the exact Bigbys source backup used ``` Do not remove rollback material immediately after the dashboard loads. Attendance imports, scheduled operations and payroll may reveal issues later. ## Final rules 1. Bigbys is the improved code source. 2. Smdummy is the experiment and must pass first. 3. Solidmark is live production and stays untouched during the experiment. 4. Port code, not production data. 5. Run ordered migrations, not Bigbys SQL-dump replacements. 6. Preserve each target's database, `.env`, uploads, branding, domain and SMTP identity. 7. Generate a unique `AUTH_KEY` per installation. 8. Keep backend authentication helpers and endpoints from one compatible version. 9. Keep frontend providers, routes, contexts and API clients from one compatible version. 10. Never use Robocopy `/MIR` for the port. 11. Never run integration tests against a database that does not end in `_test`. 12. Never deploy to Solidmark before both Smdummy and Solidmark staging pass their acceptance gates.