# cPanel installation guide

## 0. Safe first deployment
Use a NEW subdomain, NEW empty database and a separate application directory. Do not overwrite CyberPublisher or another live site. This is a read-only pilot, not the full production SRS release.

The host must have a secure, authorized network path to each router. This build has no remote collector. If your cPanel server cannot reach your private MikroTik management network, stop onboarding and arrange an approved private path with your hosting/network administrator. Do NOT expose router management broadly to the Internet to make this package work.

## 1. Required layout
Extract the ZIP using File Manager into your home directory, outside every web document root. Example:

/home/CPANELUSER/ai-network-engineer/
  config.php
  app/
  database/
  bin/
  storage/
  public/

Configure the new domain/subdomain document root to:
/home/CPANELUSER/ai-network-engineer/public

Only public/ may be web-accessible. Do not upload the whole application under public_html. If your hosting provider cannot assign this document root, ask the provider for an appropriate isolated domain layout. The application rejects a parent directory exposed as its document root.

Enable a valid HTTPS certificate for the application domain. This application does not trust arbitrary proxy headers to bypass HTTPS detection. A reverse proxy requires a server-level trusted HTTPS configuration.

## 2. PHP and database
Select PHP 8.2 or newer for the new domain. Enable curl, openssl and pdo_mysql. Use a NEW empty MySQL/MariaDB database and a dedicated database user with schema/create and normal data privileges on that database only. Do not use an existing application's database.

The package needs no Composer or Node build step on the host.

## 3. Configure privately
Copy config.example.php to config.php in the application root, not public/.
Enter the database DSN, database username and password.

Generate two independent random values using cPanel Terminal with the correct PHP binary:

php -r 'echo base64_encode(random_bytes(32)), PHP_EOL;'
php -r 'echo bin2hex(random_bytes(32)), PHP_EOL;'

Use the first as key and the second as setup_token. Do not share these values in chat. Keep a secure offline copy of key: losing it makes stored router credentials and snapshots unreadable. Do not rotate it by simply replacing it.

Set allowed_router_ips to the exact authorized management IPv4 addresses. Set router_ports to the required HTTPS ports. Use a dedicated read-only RouterOS account. Enter a trusted CA PEM bundle path in router_ca if the router uses your private CA. Certificate hostname/IP must match the connection host. TLS verification cannot be disabled in the UI.

Set timezone if needed; default Asia/Dhaka. Telegram and AI are optional and disabled/unconfigured by default.

Set config.php permissions to 0600 where your PHP handler supports owner-only files. Make storage/, storage/locks/ and storage/snapshots/ writable by the PHP/cron account, typically 0700. Never use 0777. Keep all files outside public/ private.

## 4. Run Web setup
Open setup.php on the new HTTPS domain. Enter the private setup token, administrator name, email and a unique password of 14-72 characters. The installer requires an empty database, creates schema/admin and writes storage/installed.lock.

After success, sign in, remove setup_token from config.php or set it to an empty string, and delete public/setup.php. Do not delete installed.lock. If setup fails part-way, inspect the cause and use a NEW empty database; do not manually delete tables from a live database.

## 5. Start with one router
- Companies & Groups > Create company.
- Create a group for that company.
- MikroTik Integration > Add MikroTik.
- Select company/group, hostname, pinned IPv4, HTTPS port and read-only credentials.
- Save, open the router and choose Test connection / poll now.
- Verify live resource evidence. Then test each required read menu individually.

Saving a router does not prove API connectivity. A successful resource read does not prove permissions for all other menus. Some fields/menus vary by RouterOS version.

## 6. Cron worker
In cPanel > Cron Jobs, configure a once-per-minute invocation. Use the actual PHP CLI binary and your actual home path, for example:

/usr/local/bin/php /home/CPANELUSER/ai-network-engineer/bin/worker.php >> /home/CPANELUSER/ai-network-engineer/storage/logs/worker.log 2>&1

The path above is an example, not a verified path for your host. Confirm the binary with your hosting provider. Web PHP and CLI PHP must both meet requirements. The worker uses a non-blocking lock to prevent overlapping runs.

The default per-router polling target is 300 seconds, subject to cron timing, worker budget, network latency and queue size. It is not a guaranteed real-time SLA. Snapshot schedules are hourly/daily/weekly intervals after successful capture, not exact wall-clock appointments. Poll and snapshot jobs are due-time ordered.

Check worker.log and app_meta.worker_last_run in the database after running cron. Rotate the log through your host's log management. Increase fleet size only after load and network testing. Shared-hosting process/time limits may require a dedicated collector architecture, which this release does not include.

## 7. Telegram and optional AI
Telegram: set token and chat_id in config.php. This release has ONE operator-owned destination, not per-company routing. Do not configure a customer-shared chat. Incident delivery failures are audited but no delivery retry queue exists.

AI: set ai.enabled, ai.api_key and a model that supports the fixed Chat Completions request used in app/operations.php. External API access/billing are your responsibility. Selected router resource evidence is sent externally only after an authorized user presses the explanation button. This is advisory text, not command execution. No provider key is included. Model/API compatibility has not been tested against a live account.

## 8. Pilot acceptance
Complete TESTING.md on an isolated test router and two test companies. Do not connect privileged write credentials. Do not rely on diagnostic snapshots as a recovery backup. Keep existing operational monitoring and backups in place.

## Removal
Disable cron first, revoke the dedicated read-only router account, remove the new domain/application directory and archive/delete the dedicated database according to policy. Do not touch existing sites/databases.

References:
- [cPanel Cron Jobs](https://docs.cpanel.net/cpanel/advanced/cron-jobs/)
- [MikroTik REST API](https://help.mikrotik.com/docs/spaces/ROS/pages/47579162/REST%20API)
