Deploy Node.js Apps with Flightplan
(wherever it says url.com, use your server's domain or IP)
Login to new server as root, then add a deploy user
sudo useradd --create-home -s /bin/bash deploy
sudo adduser deploy sudo
sudo passwd deploy
And Update the new password
Now login as that user
ssh deploy@url.com
Make directory .ssh on the remote server and log out
mkdir .ssh
exit
Push your ssh key to the authorized_keys file on the remote server
scp ~/.ssh/id_rsa.pub deploy@url.com:~/.ssh/authorized_keys
Note: you might have to manually copy your id_pub.rsa
file from your local machine to your vps.
Remote copying has been finnicky for me before, but generally works.
npm install -g flightplan
npm install flightplan --save-dev
var plan = require('flightplan');
var config = require('./config); //keep sensitive info in a config file that isn't checked into version control.
/**
* Remote configuration for "production"
*/
plan.target('production', {
host: config.SSH_HOST, //should be a string
username: config.SSH_USER, //should also be string
agent: process.env.SSH_AUTH_SOCK, //this actually needs to be the env variable
webRoot: '/var/www/testapp.com', // points to where NGINX is serving your static files.
ownerUser: 'root',
repository: 'https://github.com/yourgithub/testapp.git',
branchName: 'master',
maxDeploys: 10
});
plan.target('dev', {
host: config.SSH_HOST,
username: config.SSH_USER,
agent: process.env.SSH_AUTH_SOCK,
webRoot: '/var/www/dev.testapp.com/client',
ownerUser: 'root',
repository: 'https://github.com/yourgithub/testapp.git',
branchName: 'master',
maxDeploys: 10
});
plan.remote('setup', function(remote) {
remote.hostname();
remote.sudo('mkdir -p ' + remote.runtime.webRoot);
remote.with('cd ' + remote.runtime.webRoot, function() {
remote.sudo('git clone -b ' + remote.runtime.branchName + ' ' + remote.runtime.repository + ' .');
remote.log('GitHub repo successfully cloned.');
remote.sudo('npm install -g yarn');
remote.log('Yarn installed successfully.');
remote.sudo('yarn');
remote.log('Environment setup correctly.');
});
});
plan.local('deploy', function(local) {
local.hostname();
local.log('Run build');
// local.exec('npm run build');
local.log('Copy files to remote hosts');
var filesToCopy = local.exec('git ls-files', {silent: true});
local.transfer(filesToCopy, '/var/www/dev.testapp.com');
});
plan.remote('deploy', function(remote) {
remote.hostname();
remote.with('cd ' + remote.runtime.webRoot, function() {
remote.exec('pwd');
remote.log('remote work beginning.');
remote.exec('npm install');
remote.log('npm install finished');
remote.log('running npm build');
remote.exec('npm run build');
remote.log('Build successful');
})
})
Run fly
from the command line in the root of your project.
fly deploy:dev
fly deploy:production
fly setup:dev
fly setup:production
From the flightplan docs:
Scenario: 'pstadler' is the user for connecting to the host and 'www' is the user under which you want to execute commands with sudo.
$ groups pstadler
pstadler : pstadler sudo
/etc/sudoers
:pstadler ALL=(www) NOPASSWD: ALL
$ cat /etc/passwd | grep www
www:x:1002:1002::/home/www:/bin/bash # GOOD
www:x:1002:1002::/home/www:/bin/false # BAD
You can get some more info on editing your /etc/sudoers
file here. Edit this file very carefully as messing it up can have serious consequences.
You can easily add a new environment or project using this as a structure. This is a pretty extensible deployment setup that you can maintain with minimal effort.
For example, just add a new target and you can run setup
on it and it will provision you a new instance of your app.
plan.target('test', {
host: config.SSH_HOST,
username: config.SSH_USER,
agent: process.env.SSH_AUTH_SOCK,
webRoot: '/var/www/test.testapp.com',
ownerUser: 'root',
repository: 'https://github.com/yourgithub/testapp.git',
branchName: 'master',
maxDeploys: 10
});
http://usersnap.com/blog/deploying-static-websites-flightplan/
https://johnmunsch.com/2015/03/08/shipit-vs-flightplan-for-automated-administration/
https://coderwall.com/p/l1dzfw/flightplan-deploy-like-a-boss
https://geekflare.com/nginx-static-files-node-js/