Deploy to DigitalOcean from CircleCI; Overcome Permission Denied
For more than two weeks now, I’ve been trying to figure out the magic bullet to getting my builds on CircleCI to be pushed and deployed onto DigitalOcean via SSH (specifically, scp
)
Through try and error, I got one of my repos to build. As to what I did and tweaked to get it working, I couldn’t remember.
I tried another CI stuff just now, and before I forget how I got it working, I’m writing the process down here, for myself and anyone who might find it useful
Preamble
First, let’s conjoin on the same page for clarity. Here’s what this article helps achieve, specifically!
- You have a PWA Angular app you wish to deploy (technically, it could be anything, just using an Angular PWA in this instance)
- You’ve added your
config.yml
CI file (will show you one below) - After build of PWA on CI, you want the
./dist/<project_name>/*
files copied viascp
(SSH Copy, which means we’ll be needing SSH) to your DigitalOcean Droplet (It could be any VPS provider) - This tutorial assumes you already, can communicate with your remote server from your local machine (the PC/laptop you’re sitting behind) via SSH.
- At this point, if you have no idea what SSH is, you may close the browser tab, and have a nice day!
If the above is your scenario, which was mine, let’s rock and roll.
Follow these instructions carefully. I’m going to be very thorough with the steps.
Generate SSH on Remote Server
Log into your remote server, namely, the one in the cloud, in other words, the one where the files will be copied to from the Circle CI.
You ssh into the server with a command in terminal/command prompt such as ssh username@server_ip
or ssh username@domain_name
When logged in, enter these commands
NOTE: after entering ssh-keygen
, with regards to where to save the key that’s to be generated as a result of the ssh-keygen
command, type
/home/<your-username>/.ssh/for_circle
$ cd ~ $ cd ~/.ssh/ $ ssh-keygen
Now, hold your beer!
Add Public Key to authorized_keys
This step is crucial. Copy the ~/.ssh/for_circle.pub
file contents to ~/.ssh/authorized_keys
How?
cat ~/.ssh/for_circle.pub >> ~/.ssh/authorized_keys
Note: We’re using >>
so that the for_circle.pub
contents are appended to the end of the contents in the authorized_keys
file, rather than override the contents in the authorized_keys
with only the for_circle.pub
contents.
Remember, everything we’ve done so far is on the Remote Server.
Private Key to CircleCI
Now, on the server, in the previous steps, 2 files were generated from the ssh-keygen
command. We’ve only used the for_circle.pub
file. The other one is the for_circle
(without the .pub
extension).
Run this command to print the contents of the for_circle
file in your terminal, then copy the contents in your computer’s clipboard
In this case, command will be
cat ~/.ssh/for_circle
Then as shown in the GIF above, copy the entire key.
Copied?
Good. Now, navigate to your CircleCI Project settings page. Mine looks something like this:
https://circleci.com/bb/seanmavley/mazzuma-playground/edit
Now, add the private key contents you copied (the one into clipboard), paste into “Add Private Key” dialog box.
With the steps above completed, we’re left with only a single step more, namely, our .circleci/config.yml
file.
config.yml
This is the contents of the config.yml
for our PWA
# Javascript Node CircleCI 2.0 configuration file # # Check https://circleci.com/docs/2.0/language-javascript/ for more details # version: 2 jobs: build: branches: only: - master docker: # specify the version you desire here - image: circleci/node:10.12.0 working_directory: ~/repo steps: - checkout # Download and cache dependencies - restore_cache: keys: - v1-dependencies-{{ checksum "package.json" }} # fallback to using the latest cache if no exact match is found - v1-dependencies- # let's install npm - run: npm install --silent # install angular cli latest globally - run: sudo npm install -g @angular/cli@latest --silent # update - run: ng update # ng build --prod - run: ng build --prod - save_cache: paths: - node_modules key: v1-dependencies-{{ checksum "package.json" }} # copy dist files to digitalocean - run: scp -o StrictHostKeyChecking=no -r ./dist/Playground/* username@example.com://home/username/playground/ ################ WARNING WARNING ##################### # doing no strict host key check is a security risk to some extent. # But I haven't figured a way to add to ssh for both CI and DO to communicate without that # message popping up
The above file, config.yml
, kindly put it in a folder called .circleci
in your project root directory.
Moment of Truth!
Commit the config.yml
changes, and push to your repository which is tied to your CircleCi.
It should build and push to the droplet without any errors.
Troubleshooting
If all is well, you should be able to re-run your build as SSH (done from the CI dashboard), ssh into the CI Image, then from there, ssh into the remote server without any issues.