cslash / laravel-sharedsync
Deploy Laravel projects to FTP/SFTP-only hosting with incremental updates.
Requires
- php: ^8.2
- illuminate/console: ^10.0|^11.0|^12.0
- illuminate/http: ^10.0|^11.0|^12.0
- illuminate/support: ^10.0|^11.0|^12.0
- phpseclib/phpseclib: ^3.0
- symfony/process: ^6.0|^7.0
Requires (Dev)
- orchestra/testbench: ^8.0|^9.0
- phpunit/phpunit: ^10.0
Suggests
None
Provides
None
Conflicts
None
Replaces
None
README
SharedSync is a Laravel package designed for deploying applications to shared hosting environments where only FTP or SFTP access is available. It builds the project locally and performs incremental uploads to the remote server.
This package is aimed at Laravel developers who want to deploy their applications to shared hosting environments that only support FTP or SFTP (a notable example is OVH's shared hosting basic plan).
Features
- Local Pre-Build: Build project locally in an isolated temporary directory (Composer, NPM, Artisan cache).
- Incremental Deployment: Tracks changes using a manifest file (
.deploy-manifest.json) and only uploads modified files. - Dedicated Vendor Management: Fast ZIP-based remote deployment and extraction for the
vendordirectory. - FTP & SFTP Support: Works seamlessly over standard FTP or secure SFTP connections.
- Configurable Ignore Rules: Customizable ignore patterns with
.deployignorefile support. - Dry-Run Mode: Preview uploaded and deleted files before applying any remote changes.
- Selective Deployment: Deploy only specific directories using the
--onlyoption. - Remote Migrations: Trigger remote database migrations securely via signed URLs.
- Remote Health Checks: Verify storage permissions and symbolic links post-deployment.
Requirements
- PHP 8.2+ (with
ext-zipenabled) - Laravel 10.0, 11.0, or 12.0
- FTP or SFTP access to your hosting provider
Installation
You can install the package via Composer:
composer require cslash/laravel-sharedsync
Publish the configuration file:
php artisan vendor:publish --tag=sharedsync-config
Configuration
Edit config/sharedsync.php with your server details or use environment variables.
Example .env configuration:
SHAREDSYNC_DRIVER=ftp FTP_HOST=ftp.example.com FTP_USER=user@example.com FTP_PASS=secret FTP_ROOT=/public_html FTP_PASSIVE=true FTP_SSL=false SFTP_HOST=sftp.example.com SFTP_USER=user SFTP_PASS=secret SFTP_ROOT=/var/www/html SFTP_PRIVATE_KEY=/path/to/id_rsa SHAREDSYNC_URL=https://example.com
Example config/sharedsync.php:
'driver' => env('SHAREDSYNC_DRIVER', 'ftp'), 'ftp' => [ 'host' => env('FTP_HOST'), 'username' => env('FTP_USER'), 'password' => env('FTP_PASS'), 'port' => env('FTP_PORT', 21), 'root' => env('FTP_ROOT', '/'), 'passive' => env('FTP_PASSIVE', true), 'ssl' => env('FTP_SSL', false), 'timeout' => 90, ], 'sftp' => [ 'host' => env('SFTP_HOST'), 'username' => env('SFTP_USER'), 'password' => env('SFTP_PASS'), 'port' => env('SFTP_PORT', 22), 'root' => env('SFTP_ROOT', '/'), 'privateKey' => env('SFTP_PRIVATE_KEY'), 'timeout' => 90, ], 'build' => [ 'composer' => true, 'npm' => true, 'artisan_cache' => true, ], 'options' => [ 'delete_removed' => true, ], 'url' => env('SHAREDSYNC_URL'),
Important Note on Local Build
The composer build step runs composer install --no-dev --optimize-autoloader in an isolated temporary
directory. This ensures that your local development environment's vendor folder remains untouched
and the current Artisan process is not affected by the removal of dev-dependencies.
This allows you to safely enable the composer build step in your configuration.
Usage
Basic Deployment
Deploy your application:
php artisan sharedsync:deploy
Dry Run
Preview which files will be uploaded or deleted without making changes on the remote server:
php artisan sharedsync:deploy --dry-run
Force Deployment
Ignore the previous manifest and upload all files:
php artisan sharedsync:deploy --force
Selective Deployment
Only upload files from specific directories (comma-separated):
php artisan sharedsync:deploy --only=app,config,resources/views
Test Connection
Test the connection to your remote server:
php artisan sharedsync:test
List Remote Files
List files on the remote server:
php artisan sharedsync:ls
Or list a specific remote directory:
php artisan sharedsync:ls path/to/directory
Show Deployment Diff
List files that will be uploaded or updated:
php artisan sharedsync:diff
Include unchanged files in the listing:
php artisan sharedsync:diff --all
Paginate the output:
php artisan sharedsync:diff --limit=50
Vendor Management
Deploying thousands of vendor files one-by-one over FTP/SFTP can be slow and prone to connection timeouts or incomplete transfers. SharedSync provides a dedicated vendor management command to inspect dependencies and deploy the vendor directory as a compressed archive that gets extracted directly on the remote server.
php artisan sharedsync:vendor {action=list}
Available Actions:
-
List installed packages:
php artisan sharedsync:vendor list
Lists packages and versions resolved in
composer.lock. -
Compare
composer.jsonandcomposer.lock:php artisan sharedsync:vendor diff
Checks if dependencies in
composer.jsonmatch the versions locked incomposer.lock. -
Deploy vendor directory:
php artisan sharedsync:vendor deploy
Performs an optimized remote vendor deployment:
- Installs production dependencies in a clean, isolated local temporary directory (
composer install --no-dev --optimize-autoloader). - Compresses the resulting
vendorfolder into a temporary ZIP archive. - Uploads the ZIP archive to the remote storage directory (
storage/sharedsync/). - Uploads a temporary standalone PHP controller script to the remote public directory.
- Requests the controller via HTTP to extract the ZIP archive into the remote
vendor/directory. - Automatically deletes the remote controller script and archive upon completion.
- Installs production dependencies in a clean, isolated local temporary directory (
Remote Database Migrations
Run database migrations on the remote server:
php artisan sharedsync:migrate
This command generates a temporary signed URL to securely trigger the migration on the remote server. For this to work, both your local and remote environments must share the same APP_KEY.
Remote Health Checks
Run health checks on the remote server to verify storage permissions and ensure symlinks (such as public/storage) are in place:
php artisan sharedsync:check
These checks are also automatically executed at the end of every successful deployment.
How It Works
- Build: Creates an isolated temporary directory, copies the project (excluding
vendor,node_modules,.git), and optionally runscomposer install --no-dev,npm install,npm run build, and Artisan caching. - Scan: Recursively scans the build directory, applying rules from
config/sharedsync.phpand.deployignore. - Compare: Compares scanned files against the last deployment manifest (
.deploy-manifest.json). - Upload: Connects via FTP/SFTP and incrementally uploads new or modified files from the build directory.
- Delete: Removes remote files that no longer exist in the local build (if
delete_removedis enabled). - Manifest: Saves the updated
.deploy-manifest.jsonfile locally. - Remote Checks: Connects to the remote
/sharedsyncendpoint (secured with a temporary token) to verify storage permissions and symlinks. - Cleanup: Deletes local temporary build directories and the remote security token.
License
The MIT License (MIT).