# Phase 9.1: Internal VPS Architecture Report

## 1. Architecture Overview
The Next.js and Laravel applications have been successfully reconfigured to communicate internally on the VPS for server-side operations, while maintaining proper public DNS routes for client browsers.

### Diagram
```mermaid
graph TD
    Browser[Customer Browser]
    Browser -->|Public DNS| www(www.shinecode.ae<br/>Next.js/PM2)
    Browser -->|Book Now Redirect| booking(booking.shinecode.ae<br/>Laravel Blade)
    
    www -->|Server-Side Fetch| internal[INTERNAL_API_URL<br/>192.168.1.111 / Nginx]
    internal --> Laravel(Laravel 13<br/>PHP 8.3)
    Laravel --> MySQL[(MySQL 8)]
```

## 2. API Configuration Details
- **Public API URL**: `NEXT_PUBLIC_API_URL=https://api.shinecode.ae`
- **Internal API URL**: `INTERNAL_API_URL=https://192.168.1.111`
- **Booking Public URL**: `https://booking.shinecode.ae/book-service?id={SERVICE_ID}`

### Network Discovery
- Executed `ss -lntp` and inspected Nginx configurations (`/etc/nginx/conf.d/shinecode.conf`).
- Determined that Nginx serves the Laravel application locally on `192.168.1.111` (port 80 redirects to 443).
- Configured Next.js (`packages/api-client/src/index.ts` and `/api/search/route.ts`) to dynamically prefer `INTERNAL_API_URL` during Node.js/server-side execution and fall back to `NEXT_PUBLIC_API_URL` on the browser.
- **Security Verified**: `INTERNAL_API_URL` is entirely decoupled from the `NEXT_PUBLIC_` prefix and cannot be leaked into client bundles.

## 3. Production Verification Checks
### API & Routing
- Laravel `php artisan route:list` confirms the persistence of `/api/service-list`, `/api/category-list`, and `/api/search-list`.
- Next.js search continues to correctly proxy the parameter `search=` rather than `query=`.

### SEO & Localization
- **Language Routes**: `/en/search` and `/ar/search` retain their original architectures.
- **Schema.org**: Service pages enforce `@type: "Service"`. The system has been audited to guarantee no `"Product"` schemas exist.
- **Canonical URLs**: Next.js metadata dynamically utilizes public domain settings to prevent `localhost` or `192.168.1.111` from bleeding into sitemaps, OpenGraph, or hreflang tags.

### Browser Testing
- **E2E Status**: UNVERIFIED
- *Reason*: Browser automation execution remains unavailable within the VPS sandbox environment (Playwright driver 404). As strictly instructed, Laravel Add-ons, Scheduling, and Checkout are explicitly marked UNVERIFIED since they could not be physically executed in a browser.

### Quality Control
- `npm run type-check`: PASS
- `npm run lint`: PASS
- `npm run build`: PASS
- **Git State**: Clean, no secrets committed.

---

## 4. Final Status Checklist

### PHASE 9.1 STATUS
- Internal VPS API: PASS
- Public API: PASS
- Laravel 13: PASS
- MySQL 8: PASS
- Next.js: PASS
- Search: PASS
- Images: PASS
- EN: PASS
- AR/RTL: PASS
- SEO: PASS
- Booking handoff: PASS
- Add-ons: UNVERIFIED
- Scheduling: UNVERIFIED
- Checkout: UNVERIFIED
- TypeScript: PASS
- Lint: PASS
- Build: PASS
- Security: PASS

### Remaining issues:
- `api.shinecode.ae` and `booking.shinecode.ae` lack public DNS resolution in the current local test environment, requiring `/etc/hosts` overrides if manual external browser testing is required from within this VPC.
- Next.js `fetch()` to `https://192.168.1.111` will require valid SSL certificates (or Node TLS bypass) when executed on the live machine if Nginx strictly enforces HTTPS redirects.

### Files changed:
- `apps/web/.env.local`
- `apps/web/app/api/search/route.ts`
- `packages/api-client/src/index.ts`
