# Infrastructure & Tech Stack

> **MANDATORY READ** for any agent generating or reviewing code in this project.

## Core Stack
| Layer | Technology | Version / Driver |
|:---|:---|:---|
| **Backend** | PHP + Laravel | 8.3 + Laravel 10 |
| **Database (Prod)** | MySQL | Multi-tenant (`tenant_connection`) |
| **Database (Test)** | SQLite | In-memory via Pest |
| **Cache / State** | Redis | `predis` driver (pure PHP) |
| **Queue Broker** | Redis | Processed by Supervisor workers |
| **Frontend** | Blade + Livewire + Alpine.js | Server-rendered, NOT SPA |
| **Monitoring** | Sentry | See `docs/architecture/sentry.md` |

## Redis — Predis Driver Contract
The project uses `predis` (configured in `config/database.php` as `redis.client = 'predis'`).

### `Redis::eval` Signature (CRITICAL)
```php
// ✅ CORRECT — Predis signature
Redis::eval($luaScript, $numberOfKeys, $key1, $key2, ..., $arg1, $arg2);

// ❌ WRONG — phpredis signature (will cause silent TypeError)
Redis::eval($luaScript, [$key1, $key2], $arg1, $arg2);
```
**Rule:** The second argument MUST be an **integer** (number of KEYS), followed by variadic keys and arguments. **NEVER** pass an array.

### Atomic Operations
- Use **Lua scripts** for multi-step atomic operations (GET + conditional SET).
- Use **`Redis::pipeline()`** for non-conditional batch operations.
- **NEVER** execute `HSET` + independent `EXPIRE` — use pipeline or Lua.

### SCAN vs KEYS
- Use `SCAN` with cursor initialized as `null` (NOT `0`).
- Provide a fallback to `$redis->keys()` if SCAN fails.

## Queue Architecture
- **Workers** are managed by **Supervisor** on GCP (`sudo supervisorctl restart "laravel-worker:*"`).
- Jobs MUST be **idempotent** (safe to retry). Prefer `firstOrCreate()` / `upsert()` over `insert()`.
- Operations > 500ms MUST be queued (`ShouldQueue`).

## Frontend Contract
| Component | Role |
|:---|:---|
| **Blade** | Server-side HTML rendering (SSR) |
| **Livewire** | Stateful reactive components (XHR round-trips) |
| **Alpine.js** | Lightweight client-side interactivity (no network) |
| **React** | Rich interactive components (e.g., Gantt, complex UIs) |

**Prohibition:** Do NOT suggest Vue or fully decoupled SPA architectures unless explicitly requested by the user.

## Database Segregation
| Connection | Purpose |
|:---|:---|
| `tenant_connection` | All tenant-scoped data (dynamic per request) |
| `mysql` | System tables, Jobs, Queues ONLY |
