# AOPN Form Builder - Shared Hosting Deployment Guide

## Production Environment Setup

### 1. Upload Files via File Manager

Upload the following folders and files to your hosting's `public_html` or root directory:

**Required Files/Folders:**
- `app/` - Application code
- `bootstrap/` - Bootstrap files
- `config/` - Configuration files
- `database/` - Database migrations and seeders
- `public/` - Public assets (this should be your document root)
- `resources/` - Views and assets
- `routes/` - Route definitions
- `storage/` - Storage directory
- `vendor/` - Composer dependencies
- `.env` - Environment configuration (create from template below)
- `artisan` - Laravel CLI
- `composer.json` & `composer.lock`
- `package.json` & `package-lock.json`
- `vite.config.js`

**Do NOT upload:**
- `.git/` - Git repository
- `node_modules/` - NPM dependencies (rebuild on server)
- `tests/` - Test files
- `.gitignore`, `.env.example`

### 2. Create .env File

Create a `.env` file in your root directory with the following configuration:

```env
APP_NAME="AOPN Forms"
APP_ENV=production
APP_KEY=base64:YOUR_GENERATED_KEY_HERE
APP_DEBUG=false
APP_URL=https://forms.aopn-ng.org

APP_LOCALE=en
APP_FALLBACK_LOCALE=en

APP_MAINTENANCE_DRIVER=file

BCRYPT_ROUNDS=12

LOG_CHANNEL=stack
LOG_STACK=single
LOG_LEVEL=warning

# Database Configuration (MySQL)
DB_CONNECTION=mysql
DB_HOST=localhost
DB_PORT=3306
DB_DATABASE=aopnforms_db
DB_USERNAME=your_db_username
DB_PASSWORD=your_db_password

SESSION_DRIVER=file
SESSION_LIFETIME=120
SESSION_ENCRYPT=false
SESSION_PATH=/
SESSION_DOMAIN=.aopn-ng.org

BROADCAST_CONNECTION=log
FILESYSTEM_DISK=local
QUEUE_CONNECTION=sync

CACHE_STORE=file

# Mail Configuration (SMTP)
MAIL_MAILER=smtp
MAIL_HOST=mail.aopn-ng.org
MAIL_PORT=587
MAIL_USERNAME=noreply@aopn-ng.org
MAIL_PASSWORD=your_mail_password
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS=noreply@aopn-ng.org
MAIL_FROM_NAME="AOPN Forms"

VITE_APP_NAME="AOPN Forms"
```

**Generate APP_KEY:**
If you have SSH access, run: `php artisan key:generate`
Otherwise, generate one locally and paste it in.

### 3. Set Directory Permissions

Via File Manager or cPanel File Manager, set the following permissions:

```
storage/ and subdirectories: 755
bootstrap/cache/: 755
public/storage/ (symlink): 755
```

If your host requires, set `storage/` to `777` (but this is less secure).

### 4. Import Database

1. Export your local database:
   ```bash
   mysqldump -u root -p aopnform > aopnform.sql
   ```

2. Import via cPanel/phpMyAdmin:
   - Create a new database named `aopnforms_db`
   - Create a database user with full privileges
   - Import the `aopnform.sql` file

3. Run migrations (if starting fresh):
   ```bash
   php artisan migrate --force
   php artisan db:seed --force
   ```

### 5. Create Storage Symlink

Run this command to link storage to public:
```bash
php artisan storage:link
```

If you don't have SSH access, manually create the symlink or copy `storage/app/public` to `public/storage`.

### 6. Build Frontend Assets

If you have Node.js access:
```bash
npm install
npm run build
```

If not, the pre-built assets in `public/build/` are already included.

### 7. Clear Caches

```bash
php artisan config:clear
php artisan cache:clear
php artisan route:clear
php artisan view:clear
php artisan optimize
```

### 8. Configure Document Root

Ensure your hosting's document root points to the `public/` folder, not the project root.

If using cPanel:
- Go to "Select PHP Version" → "Switch to PHP Options"
- Set `open_basedir` to include your full path
- Ensure `allow_url_fopen` is On

### 9. .htaccess Configuration

Create `.htaccess` in the `public/` directory:

```apache
<IfModule mod_rewrite.c>
    RewriteEngine On
    RewriteBase /

    # Handle Authorization Header
    RewriteCond %{HTTP:Authorization} .
    RewriteRule .* - [E=HTTP_AUTHORIZATION:%{HTTP:Authorization}]

    # Redirect Trailing Slashes
    RewriteCond %{REQUEST_FILENAME} !-d
    RewriteCond %{REQUEST_URI} (.+)/$
    RewriteRule ^ %1 [L,R=301]

    # Handle Front Controller
    RewriteCond %{REQUEST_FILENAME} !-d
    RewriteCond %{REQUEST_FILENAME} !-f
    RewriteRule ^ index.php [L]
</IfModule>

# Security Headers
<IfModule mod_headers.c>
    Header set X-Content-Type-Options "nosniff"
    Header set X-Frame-Options "SAMEORIGIN"
    Header set X-XSS-Protection "1; mode=block"
</IfModule>

# Disable Directory Browsing
Options -Indexes

# Protect Sensitive Files
<FilesMatch "\.(env|git|log)$">
    Order Allow,Deny
    Deny from all
</FilesMatch>
```

### 10. Test the Application

1. Visit `https://forms.aopn-ng.org`
2. Should redirect to login page
3. Login with admin credentials
4. Test form creation and submission

## Post-Deployment Checklist

- [ ] APP_DEBUG is set to false
- [ ] Database credentials are correct
- [ ] Storage directory is writable
- [ ] Storage symlink is created
- [ ] Mail configuration is working
- [ ] SSL certificate is active
- [ ] File uploads are working
- [ ] Public form is accessible
- [ ] Admin dashboard loads correctly

## Troubleshooting

### 500 Internal Server Error
- Check `.env` file exists and is readable
- Verify database credentials
- Check storage permissions
- Review `storage/logs/laravel.log`

### 404 Not Found
- Ensure document root points to `public/`
- Verify `.htaccess` is in `public/`
- Check mod_rewrite is enabled

### File Uploads Not Working
- Set `upload_max_filesize` and `post_max_size` in php.ini
- Verify `storage/app/public` is writable
- Check folder permissions

### Email Not Sending
- Verify SMTP credentials
- Check if port 587 is open
- Test with mailer set to `log` first

## Security Notes

1. **Never commit `.env` to version control**
2. **Keep Laravel updated** - run `composer update` regularly
3. **Use strong database passwords**
4. **Enable SSL** - force HTTPS via `.htaccess`
5. **Monitor logs** - check `storage/logs/laravel.log` regularly
6. **Backup database** - set up automated backups

## Force HTTPS (Optional)

Add to `.htaccess` in `public/`:

```apache
RewriteCond %{HTTPS} off
RewriteRule ^(.*)$ https://%{HTTP_HOST}%{REQUEST_URI} [L,R=301]
```

## Support

For issues, check:
- Laravel documentation: https://laravel.com/docs
- Hosting provider's support
- Application logs: `storage/logs/laravel.log`
