Skip to content

The End of The Year, Deployment, and The 12Factors App

It's finally that time of the year again. No matter where your eyes were looking at, everything was covered by a thick white blanket. The cold slowly pierced your skin as you moved. Even a litte touch felt like a sharp blade. The further you walked, the more painful it became. The office door seemed so far away. You really wished you were in your bed, covered by a warm blanket and accompanied by a glass of piping hot tea right now. In reality, you were sitting at your desk.

Although all your tasks were done, you still needed to remain present at the office until the deployment is complete. It was a peaceful and relaxing day for you and the rest of the backend team, except for Alex. He was still busy with the deployment related stuff. He had a rather stiff expression since this morning. The loud sound of the keyboard's typing reverberated in your ears. Every few minutes, he gave a long sigh. As if something disappointed him every so often. You didn't even need to ask what's wrong. His face told you everything you needed to know.

"Is there something wrong with the codebase? " That line was simply courtesy. You knew something was wrong. Alex glared coldly at you, as if it wasn't cold enough. He stopped for some seconds before gesturing for you to look at his monitor.

"I really need to teach you guys something about the 12Factors App. It is always a pain to deploy your codebase."

Something made you regret your decision to chat with him. But, it has already happened so you decided to stay. Alex then started to speak, explaining the list of problems in his monitor.

"I believe you are familiar with 12Factors App?"

"No." You responded quickly. Alex looked annoyed. After taking a deep breath he accepted the fact and continued.

"It seems we need to start from zero."

You didn't know exactly whether he had the time for all of this knowing the deadline was near, but you listened anyway.

"Since we will use a third party service as our deployment platform this time, I want to show you a methodology that is widely used to develop and deploy such an application. It’s called 12Factor. Yeah normally we won’t need to follow this methodology, as the client also seems not to care much about it, but I want give my best and show them an app built by best practices. After all, they might change the deployment platform in the future. Following this best practice is for our best interests in case that happens."

Alex revealed his plan on the monitor. It listed everything, starting from the current codebase until the development platform and what improvements should be done.

“ We will use Heroku as a deployment platform. Until now we've used a development environment to develop and when the deployment stage was coming, I just changed some settings to match the production environment and deployed them manually. However we can automatically deploy a new version of our application using CI job. Heroku, fortunately, supports it as well. But, deployment is only a small part of our concern right now. Here, look. “

A list of problems showed up. The problems were not bugs or a faults in the program, but it is a list of issues of 12Factors that are not yet fulfilled by the current application.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
1. Codebase: X - no staging and production development, only development
2. Dependencies: V - Using Gradle automatic build system
3. Config: X - Some variables are hard coded
4. Backing Service: V - Using dependencies system)
5. Build, Release, run: X
6. (Not included)
7. Port Binding: X and V. Need to be declared specifically in applications.properties
8. (Not included)
9. (Not included)
10. Dev/Prod parity: X need to ensure point 3, since hard coding makes it coupled to local development environment
11. Logs: X Some classes don't have loggers and some of the debugging’s print are not yet using logger.
12. Admin processes - V has been implemented by spring boot by default.

"I don't understand." You replied.

"Yeah I expected that. "

"Thank you."

Alex looked even more irritated. You expected him to stop, but instead he began to explain more and more things to you. If you hadn't regretted your decision to initiated a talk with him earlier, now you definitely would. However, this is knowledge you never heard of before. You found it interesting. So you didn't try to run away.

Alex took about half an hour to explain everything. After you showed good understanding, Alex seemed satisfied. But as soon as he glanced at the clock, a frown returned to his face.

Alex was an interesting person. He seemed like he didn't care about your team. He wasn't a good leader either. He even admitted that himself. However, once you've discussed something that gained his full attention, he would immerse himself in it, ignoring everything else. Maybe only the presence of Maya, the frontend team lead, may be able to bring him back to the reality.

"Can I help refactor the codebase?" You then decided to help him out since he took his time to explain everything. You also had understood the task you need to do in order to complete the 12Factor, so it won't take too much effort to complete. After all you had completed all the tasks given to you.

"Sure. That will help me a lot." He simply replied.

Codebase

Any application should have exactly one codebase. At the moment, The application has one environment, that is development environment. The codebase constraint restricts the application without regarding the number of servers that run the application. This means every server that runs the application must use the same codebase.

Checklist

  • Create a branch named “staging”.
  • Create a Heroku account if you still don’t have one.
  • Create a Heroku app named “trade-system-< NPM> -production” where is your student identification number ( also eponymously known as NPM). This will be your production environment. Ex: trade-system-20012233434-production
  • Create another Heroku app named “trade-system-< NPM >-staging” where is the same value from before. This will be your staging environment.
  • Create Heroku Postgres instances for both servers.
  • Deploy the application to both servers. You must deploy the code from the “master” branch to the production environment and deploy the code from the “staging” branch to the staging environment. (Hint: You might want to solve the “Build, release, run” constraint’s task to do this)

Config

The application configuration in application.properties needs to not include sensitive information like database username, password. Their values has to be taken from environment variables.

Checklist

  • Analyze all variables in the application.properties. List all dangerous variables that store sensitive information.
  • Make environment variables to store sensitive information
  • Refactor application.properties to use the environment variables.

Build Release and Run

Application deployment should be separated into three stages: build, release, run.

Build stage is when “transformation” of the application’s code into executable files is done. Release stage is when the application’s code that already passed the build stage is sent to the deployment’s environment (for example: staging and deployment). Run stage is when the application’s code that passed the release stage is run (in the designed environment in release stage). Your job is to make the deployment flow into these stages.

Checklist

  • Create build and release stages into your practical-6’s “.gitlab-ci.yml”. Make sure to differentiate release stages for staging and production environments.
  • Add a new job to deploy your practical-6 application.
  • Make sure not to expose sensitive information related to your Heroku apps and account. (Hint: Satisfy the Config constraint)

Port Binding

As a web application it is common sense that it will run on port 80. But this time you want the service to serve at 8089. It also makes the application have an universal port.

Checklist

  • Change the port at application.properties

Dev/Prod parity

At the current state, the application will run smoothly in a local development environment. It will not run at Gitlab or Heroku. Provide the each environment (refers to staging and production at point 1) the variable needed to run the application. At the current state, the application has been using the same database driver as the production. You just need to make sure the data sources are correctly configured. In the ideal condition, the OS that runs the application should be the same in all environments. But you will assess this issue later.

Checklist

  • Provide all the variables needed in the repository as well in Heroku.

Logs

The last thing you need to do is to implement a logging system. During production, we don’t always want all the system’s information to be displayed. Say we print out every little detail using System.out.println(). Sometimes we don’t want this information to leak, or sometimes it returns a simple confirm message which isn’t really necessary. This is bad granularity. Using a logger, we can control the levels of logging output we want.

There are several ways to implement a logger, either with java.util or an external application. You are not confined to only one method to log messages to the console. The main point is to treat your logs as event streams, and output to stdout. What the environment chooses to do with these event streams are of the environment’s concern. All the application needs to do is output logs based on the events that are happening within the application.

Checklist

  • Implement a logging system for the functions. Make sure it can return an output to stdout. You are allowed to use any logging system you want.

Notes

You need to configure a local PostgreSQL database in order to run the application. You can set the configuration via application.properties to match with your local database.


Last update: 2022-03-22 21:58:02
Created: 2022-03-22 21:58:02
Back to top