I’ve been learning and using Rails for about a year and a half now. I’ve built a lot of little internal Ruby apps and Rails web apps for managing our data, and getting some mustard cut. This week I earned a new achievement: I’ve launched a public facing web app for our company. It’s nothing to really link to, since it’s still an internal app for certain types of data management and reporting, but it’s hosted on the other side of my firewall (and it’s terrifying).
The current development/deployment process I’m using is pretty sweet, and I love this new routine.
My code is hosted on a GitLab server I’ve been running internally for about two years. If you aren’t in on the GitLab stuff, you really should check it out.
GitLab has powerful built-in CI and deployment tools and it’s been a major source of my inspiration for understanding and championing devops type activities.
When a commit arrives in the master branch, GitLab deploys my code and secret environment variables to a server running Docker, where an image is built and
rake test is run.
To me, Docker has become key because I don’t have to worry about setting up a Rails environment on every (any???) machines – I can just use a reliably set up image that I’ve already customized to my needs (
FROM Ruby with node and an image processor installed). With Docker, any machine lying around can run all sorts of languages without having to worry too much about configuration. Sweet.
I (very simply) added test coverage statistics using a gem called Coveralls. It took minimal effort to set up, and gives me powerful statistics. GitLab can parse my test results for the test coverage percentage, and shames when it’s low. Coveralls directs me to where my code may be lacking tests. It doesn’t help me write good tests, but it at least gives me a place to start, and has helped me get into the practice of using them at all.
GitLab allows you to save artifacts from your run and download them from the web interface. This is powerful for all sorts of applications:
- Your compiled application could be easily downloaded and distributed as a zip.
- A data application that was otherwise a simple console application can suddenly create reports for someone to download from a web interface with the press of a play button.
- My current use case: Certain logs or reports could be created and accessed from the web interface. Coveralls generates reports and saves them as a simple HTML site in a directory. I set the coveralls directory as a build artifact– and now for every CI run, I can browse the test coverage results in a way that really helps pin specific issues down.
When your build starts in GitLab, you can see the console screen as if your web browser were your terminal. All output is sent to your screen.
If one of your commands returns a non-0 result (i.e. an error occurred) the CI workflow can stop (or continue) and report back. GitLab can also parse all of this output for a string that represents test coverage and add a little badge to my project page to make me feel bad when I have untested code, or awesome when I’m actually using testing at all. Even just being conscious of untested code makes me much more conscious about maintaining and writing good tests.
Once GitLab receives a green light from my test container, it ships the code off to get packaged up for deployment to a staging server. I am able to build my app in an environment-agnostic way, sending the correct variables depending on where I’m running the container. For the next step, I build the application and run it on a staging server for internal review.
Finally, when I’m super impressed and everyone is chanting my name in triumph, I press a play button, and poof: my container gets sent off to the production server and started up with the appropriate env vars. All I had to do was press play.