Continuous integration is a software development practice where programmers integrate their source code changes frequently and whose goal is to detect errors as early as possible.
This is the first article for a series where we'll show how to create a continuous integration server for PHP projects. In this first article we analyse the tools that we're going to use.
The goal of this article is to show you the tools we're going to use for a PHP project. We'll also talk about some alternatives. In the following articles we'll show you how to install these tools to end up with the following continuous integration flow:
Each software group and application would give an article and the point of this article is to provide a short descriptions of all the tools we'll use. Keep in mind that, based on your needs, you may need to use more suitable tools and I recommend you to take a look at the available options before you commit to one.
Version control system
We'll start with version control systems which is "mandatory" in any software development team, even if there's only one team member. Briefly, a version control system records all the changes made to the project files (specifically, source code files), when they were made and by whom.
When you're choosing a version control system, it's important to know the difference between a DVCS (Distributed Version Control System) and a CVS (Concurrent Version System).
DCVS systems have a central repository and that repository is "replicated" for each client (programmer). With a DCVS system you can have multiple programmers working on the same source file. When they commit (send the changes to the central repository) their changed files, a merge occurs. Another advantage is the possibility to change the source code without the need to be connected to the central repository, so you can work at home or on your way to work.
CVS systems only have the central repository and require that each file is changed by only one programmer at the same time (known as checkout) and you need to be connected to the central repository to register your changes (checkin).
The most common solutions are:
In this series of posts we'll implement Git because:
- It's a DCVS, which provides more flexibility
- Probably has the larger user community, hence, more online information
- It's quite simple to use
Project, tasks and bug management
A task and bug management allows you to register all the changes to the software from the functional point of view. That is, it allows you to view and edit the changes made to the software without the need to search the entire code base.
There are multiple advantages on using a project management tool and the most common are the ability to know what has changed in a specific release. In some cases it even allows your clients to view or add scheduled changes to the software.
There are a few solutions, commercial and free. The most popular are:
|Commercial software||Free software|
|Jira (Atlassian)||YouTrack (JetBrains)||BugZilla (Mozzila)||Redmine||Trac (Edgewall)|
In this series we'll implement Redmine, a free software developed with Ruby on Rails that:
- Allows you to create multiple projects
- Has a lot of plugins so you have more flexibility
- It's simples and it's not ugly
- Allows you to create multiple versions / releases
- Logs the total amount of time spend by each programmer and for each task
Continuous integration software
Continuous integration software is the "glue" that holds all the other parts together. Their basic operation is:
- Have mechanisms to trigger a build
- Fetch the latest source code from the central repository of the version control software
- Run a bunch of commands (defined by you)
- Produce metrics and artifacts
A build is a process that has a set of steps, triggered by an action that produces artifacts. A more specific example of a build can be:
- Triggered every time a programmer commits some changes
- When triggered, the following steps occurs:
- Fetch the latest source code from the version control
- Run all or a set of automated tests
- From the automated tests, produce metrics for quality control
- Generate artifacts to use in production environment
Usualy these steps are sequentially and exclusively. This means that if a step has some error, the following steps are not executed.
There are a few commercial and free tools for continuous integration each one with it's pros and cons. When you choose your tool it's important to know what programming language each tool supports and what is their restrictions. For instance, not all tools support PHP projects, but most of them support Java and .net.
- Interface: open source projects lack good interfaces. This is the case of Jenkins which can be even better than TeamCity but it's, well, not intuitive
- It's free: you can use TeamCity for free as long as you don't exceed the maximum of 20 builds and 3 agents
- IDE: TeamCity integrates well with PHPStorm IDE (since both tools are maintained by JetBrains), which I consider the best IDE for PHP projects
As I said, each build has a set of steps that should be executed and, if you want to use TeamCity for free you can have up to 20 builds. Build examples:
- Build to run all unit tests whenever a commit is performed
- Build to run every automated tests (unit, functional and acceptance) once a day
Agents are the machines (computers) where the builds steps are executed and you can use up to 3 with the free version. It's possible to install an agent in the same machine there you have TeamCity but you can also install the agents in independent machins.
For instance, if you are developing a PHP project that has to be served in Windows and Linux, you can setup two agents:
- One agent which has Linux and serves PHP with Apache
- One agent which has Windows and serves PHP with IIS
This way, if you use Selenium to perform acceptance tests you can ensure the layout and interface is similar in both environments.
The usage of multiple agents is useful and recommended for any project because it allows you to execute your software with different configurations. If you develop software for Windows with C# you can guarantee that your software works with different versions of Windows (Windows Vista and Windows 8, for instance).
Metrics and quality control
The main goal of a CI is to guarantee your software quality. However, it's not enough to develop and execute automated tests. You need something that shows you the big picture on how you're doing.
For that we will use SonarQube, which can analyse projects from various programming languages (Java, .net and PHP, to name a few). The information that we want to retrieve from SonarQube is:
- Code Coverage: what's the percentage of code that is covered by automated tests
- Total number of lines of code (LoC), classes and files
- How much commented code you have (total number of lines of comments)
- Percentage of code that is duplicate
- Technical debt
- And, more important, what can you do to improve your code
Technical debt represents the amount of time that you need to correct and improve you project. If your code is too complex (too many nested loops, too large methods, ...) of if you don't code according to the used coding standards you'll end up with a high technical debt. Unless you keep an eye on this, the debt will keep growing.
As you can imagine, the lower the debt the more maintainable the project.
There are other solutions like Squale. I fell in love with SonarQube since I began to work with it because it's a very simple, intuitive and powerful tool. So, that's the reason why we'll stick with it.
Installations and configurations
In the following articles we will install these tools in a server with Linux Mint 17.1. If you want to set up a CI server for production purposes, I recommend you use CentOS. You should also choose a LTS (Long Term Support) version to keep it easy to upgrade (because long term support versions maintain the update repositories for a few years).
This article is a part of the series "How to set up a Continuous Integration Server for PHP projects".
- Tools for a Continuous Integration (CI) server for PHP projects
- Install SSH and Git on Linux and configure a Windows development machine
- Install Redmine and integrate it with Git
- Install and configure TeamCity 9
- Install and configure TeamCity Agent on Linux Mint
- Install SonarQube and SonarQube Runner on Linux Mint
- Analyse a Laravel 5 (PHP) project with SonarQube
- Integrate SonarQube with TeamCity and Redmine