Development on PaaS with dokku heroku - mavenea/mavencrm GitHub Wiki
dokku prep
- install dokku on the host or use vagrant for local dev.
the following plugins are useful and used by our configuration
**docker-direct**: dokku plugin to issue docker commands directly
dokku plugin:install https://github.com/josegonzalez/dokku-docker-direct.git docker-direct
**require**: dokku plugin to setup all the requirement for your app on push
dokku plugin:install https://github.com/crisward/dokku-require.git require
**memcached**
sudo dokku plugin:install https://github.com/dokku/dokku-memcached.git memcached
**rabbitmq**
sudo dokku plugin:install https://github.com/dokku/dokku-rabbitmq.git rabbitmq
**mysql**
sudo dokku plugin:install https://github.com/dokku/dokku-mysql.git mysql
# useful for development environment
**nuke**: stop all running containers, then delete all containers and images
dokku plugin:install https://github.com/josegonzalez/dokku-nuke.git nuke
**apt**: Inject deb packages into dokku based on files in project
sudo dokku plugin:install https://github.com/dokku-community/dokku-apt apt
#set mode to dokku_dev as defined in app.json. default is `dokku`
dokku require:mode dokku_dev
example for local dev.
- install dokku with vagrant. make sure that port 8080 and port 22 are free on the host.
git clone https://github.com/dokku/dokku.git
vagrant up
- ssh to the running machine. you can use
vagrant ssh
service forwarding is running on the maching on port 2222 which is forwarded to the dokku virtual machine ssh server listening on port 22. the service is listening only on loopback interface, so this means that dokku cannot be accessed from any other machine using ssh. If we want to ssh from a different machine the virtualbox port forwarding rules need to be changed and allow this. To do this remove the loopback IP Address from Host Network Manager of the VirtualBox NAT adapter port forwarding rules for the dokku virtual machine.
- get the private_key created during installation and add it to ssh-agent or use it directly when ssh to the machine. Note: the machine public key usually at
~/.ssh/id_rsa.pub
should already be copied to the machine if file exists, however, in my case this did not happen for some reason.
vagrant ssh-config dokku
IdentityFile
is the path to the automatically generated private key which is already installed on the dokku virtual machine under~/.ssh/authorized_keys
. We can use the generated private key to connect to the host by either adding to the localssh-agent
(recommended) usingssh-add /path/to/identity/file
or by providing the path to the private key withssh
command. You can also copy the key to the ~/.ssh directory and usessh-add
with no arguments - it automatically adds all keys in ~/.ssh to the keystore. I prefer to use a single set of keys rather than manage different service keys, so I use my own public/private key pairs for each machine I use.
User
is the user to use for ssh. The user name isvagrant
in this case.
- ssh to the host
ssh -i /path/to/identity/file/ [email protected]
or if you added theIdentityFile
tossh-agent
then just simplyssh [email protected]
. The same key is also automatically added todokku:ssh-keys
to enable ssh remote git push.
verify ssh-keys are added to
dokku
using
dokku ssh-keys:list
other way of connecting from the local machine is using
vagrant ssh
from the same folder. if need to copy another ssh public key, login usingvagrant ssh
and then copy the new public key to~/.ssh/authorized_keys
then run
# usually your key is already available under the current user's `~/.ssh/authorized_keys` file
# the name admin is significant check dokku docs
cat ~/.ssh/authorized_keys | sudo dokku ssh-keys:add admin
- enable global vhosts and domain. During installation domain is already configured to
dokku.me
.
Verify domain is configured
dokku domains:report --global
=====> Global domains information
Domains global enabled: true
Domains global vhosts: dokku.me
if not
dokku domains:set-global dokku.me
Tip: the domain
dokku.me
is actually internet resolvable domain name! It is a sneaky turnkey solution for getting your local machine up and running in no time without having to mess with hosts file. In fact it maps any host (that is, *) to10.0.0.2
which is usually the hostdokku
built when usingvagrant up
command :) the local port forwarding rule takes care of the rest!
notice you can ping the dokku host using
ping dokku.dokku.me
orping dokku.me
.
virtualbox dokku machine configured a new host NAT network with IP
10.0.0.1/24
.dokku.dokku.me
host IP is10.0.0.2
along with all subdomains (i.e. yourapp.dokku.me). Verify byping dokku.me
from the host.
more details https://github.com/dokku/dokku/blob/master/docs/getting-started/install/vagrant.md
app deployment (heroku/dokku/etc.) PaaS
now that dokku is up and running, we shall create the application and configure it. The steps should be generally similar if using heroku.
# create the app
dokku apps:create mavencrm
# clear any assigned domains
dokku domains:clear mavencrm
# enable vhosts support
dokku domains:add mavencrm dokku.me
dokku domains:enable mavencrm
dokku domains:clear mavencrm
# verify vhost
dokku domains:report mavencrm
- create the mysql service and link it
# on 0.19.x+
sudo dokku plugin:install https://github.com/dokku/dokku-mysql.git mysql
dokku mysql:create mavencrm-db
# link mysql service
dokku mysql:link mavencrm-db mavencrm
# dev-only use apt-packages plugin to inject xdebug into the environment
# on dokku 0.18.x+
sudo dokku plugin:install https://github.com/dokku-community/dokku-apt apt
# apt-packages file on the root `web` directory include `php-xdebug` which will be injected on deploy.
- specify os stack to use ubuntu 20 base os instead of the default Ubuntu 18 base OS
dokku buildpacks:set-property mavencrm stack gliderlabs/herokuish:latest-20
buildpacks required are detected automatically, however, this is a multi-buildpack setup. File named
.buildpacks
exist on the root directory which is used to let heroku/dokku know which buildpacks to use.
- deploy the app
# from your local machine mavencrm folder
# the remote username *must* be dokku or pushes will fail
cd mavencrm
git remote add dokku-remote [email protected]:mavencrm
# push to the remote branch called master - default branch in dokku/heroku
git push dokku-remote dev:master
-----> Cleaning up...
-----> Building mavencrm from gliderlabs/herokuish:latest-20
-----> Setting config vars
CURL_CONNECT_TIMEOUT: 90
-----> Setting config vars
CURL_TIMEOUT: 600
-----> Adding BUILD_ENV to build environment...
-----> PHP app detected
remote: -----> Bootstrapping...
remote: -----> Installing platform packages...
remote: - php (7.4.22)
mounting source code files
we going to mount the local source directory to a mountpoint in the dokku box. This solution will later enable us to create a nice multi container solution.
default
Vagrantfile
of dokku require the following changes:
# disable out of box /vagrant mountpoint
# `vagrant halt` then we create a mount point owned by `vagrant` user by editing Vagrantfile and add
config.vm.synced_folder ".", "/vagrant", disabled: true
# herokouish buildpacks are used for the app therefore the uid and gid
config.vm.synced_folder "/path/to/source/files/mavencrm", "/mavencrm", mount_options: ["uid=32767", "gid=32767"]
#add postfix to apt-get install command to enable cron email
postfix
#then
vagrant up
then we can do
dokku storage:mount mavencrm /var/lib/dokku/data/storage/mavencrm/web:/app/web
#restart the app
dokku ps:restart mavencrm
copying shared source code directories to VPS
#install rclone & configure using rclone config
#use rclone copy
rclone copy remote:yoursourcecodefiles/mavencrm/web web --transfers 32 --progress --fast-list --ignore-times --no-check-dest --no-check-certificate
# gid & uid must be 32767:32767 - as mounted to herokuish will require ids to match /app/
cd /var/lib/dokku/data/storage && sudo mv ~/mavencrm mavencrm && sudo chown -R 32767:32767 mavencrm
# now we can either manually mount or use require plugin which will mount automatically based on `volumes` key in `app.json`
cron setup
dokku
app.json
entry to create a cron schedule looks like the below
"cron": [
{
"command": "$SHELL web/cron/RunCron.sh >/dev/null 2>&1",
"schedule": "*/5 * * * *"
}
],
note: cron is now setup using
sleep
. this ensures that cron runs in its dedicated container. executable isRunSleep.sh
defined inProcfile
install postfix in Vagrantfileapt-get install
in order for cron to send mail notification of errors otherwise you would get “(CRON) info (No MTA installed, discarding output)” error from the syslog.grep CRON /var/log/syslog
to see the log for troubleshooting.
cat /var/mail/root
to view the mail received from cron - stating errors if a cronjob fails to work
storage using rclone
rclone copy remote:path folder --transfers 32 --progress --fast-list --ignore-times --no-check-dest --no-check-certificate