I have never used a Continuous Integration system (CI) before. I primarily code in MATLAB, Python or PHP. Neither of these have a build step and I do not see how a CI could be used for my work. A friend on a large project in a large firm told me that language does not matter.

I do not see how CI would be of use to me if I do not have a build step. I can think of CI as a testing environment that would run unit tests. Am I missing something?

  • 8
    "These things are orthogonal..." – gnat Feb 19 '16 at 18:20
  • 14
    Whether this is true depends on what you consider a "build step" to be. You seem to think of it as just the bare minimum compilation, to give you something runnable. In my team, we consider build to be compilation, static analysis, and unit tests (with room for more tasks). This definition has the advantage that a commit which fails unit tests does not "build" and isn't allowed into the repo to begin with. – Chris Hayes Feb 19 '16 at 19:10
  • Expanding on Chris' point, a CI system can and should test any and all automated tests - compiling and linking can be seen as one form of automated tests. If you have resource constraints some of the slower tests may only run on nightly builds, or even weekend builds, but CI will run them. Ask yourself this: Why would you want to automate tests but still run the automated tests manually? – Peter Feb 20 '16 at 23:16

Continuous integration as a term refers to two distinct ideas.

The first is a workflow: instead of everyone in a team working on their own branch and then after a couple of weeks of programming try to merge their changes into the mainline, that changes are integrated (nearly) continuously. This allows problems to surface early, and avoids incompatible changes. However, that requires that we can easily check whether a change “works”.

This is where the second idea comes in, which turned out much more popular. A CI server is a clean environment where the changes are tested as quickly as possible. The clean environment is necessary so that the build is reproducible. If it works once, it should always work. This avoids “but it worked on my machine” problems. In particular, a CI server is valuable when your software runs on different systems or in different configurations and you need to be sure everything works.

The lack of a build step is irrelevant. However, CI only makes sense if you have a test suite. This test suite must be automatic, and must have no failures. If the tests fail, the appropriate developer should get a notification so that they can fix the problem they introduced (“breaking the build”, even when there is no build as compilation).

It turns out that such a server is valuable for more than just testing. In fact, most CI software is really crappy at running tests in various configurations, but good at managing all kinds of jobs. E.g. in addition to “continuous” unit tests, there could be a full test as a nightly build. The software can be tested with multiple Python versions, different library versions. A web site could be tested for dead links. We can run static analysis, style checkers, test coverage tools, etc. over the code. Documentation can be generated. When all test suites pass, the packaging process could be initiated so that you would be ready to release your software. This is useful in an agile setting where you want a deployable (and demoable) product at all times. With the rise of web apps, there's also the idea of continuous deployment: If all tests pass, we can automatically push the changes to production. Of course, this requires that you are really confident in your test suite (if not, you have bigger problems).

  • 3
    "CI only makes sense if you have a test suite" - note that for a compiled language, the compiler itself is a rudimentary test suite that catches many common errors. – user253751 Feb 20 '16 at 23:10
  • @immibis I think that is not about compiled vs. interpreted, but about static typing. A language with a static type system can automatically prove certain correctness properties. This is even better than tests which just work by examples. The only common problem found by a CI server when doing a compile is that a dev forgot to commit a new file; in all other cases we don't really need a CI server and could just compile locally to check for errors. – amon Feb 21 '16 at 9:14
  • 1
    @amon Untrue. It is not especially uncommon to make a last minute change and then forgetting to test the compile before committing. It also catches problems when you add dependencies on something you have globally installed locally but isn't installed anywhere else. – jpmc26 Feb 22 '16 at 18:13

True, you do not have particular need of a CI system to perform builds and check that those builds are correct, but that is only part of what CI is about.

The purpose of CI is to detect errors as soon as possible, because generally speaking, the earlier an error is caught the cheaper it is to fix. To that end, in the case where a build step is not necessary, a CI system can still automate the use of code analysis tools, deployment to a testing environment, unit/integration/regression/other testing you can automate, and any other steps you can automatically perform in order to check for errors.

  • 8
    I'd add: the most obvious way to auomatically test the system is to automatically execute it. E.g. you can test a website using tools such as JMeter or Selenium. – reinierpost Feb 19 '16 at 19:00

Continuous integration performs more than a compile of the code. If that's all it did, then we wouldn't need nearly so many tools for it!

Some other tasks I can think of off-hand that a continuous integration pipeline often performs:

  • Executing automatic tests. (Python has a wealth of automated testing libraries, and PHP has at least some. I can't speak to MATLAB.)
  • Bundling the software for distribution. By automating this process, you ensure that it is done in an exact, consistent, repeatable fashion every single time. No steps will be forgotten; generating such a distribution package takes at most one click. (Bundling your Python app as a wheel is a great idea!)
  • Tagging milestone commits. Whenever you build a package for production, you probably want to tag it.
  • Auto-incrementing version numbers. Usually this would just be the "build" number and not the more meaningful parts, but it can be nice to uniquely identify a particular build, so you know what is deployed where.

Going a little further to the border line of "continuous integration" in a strict sense, you could also do these:

  • Have an automated process for setting up an operating system and installing your dependencies.
  • Automatically deploying copies of the software (primarily useful for web applications or software distributed by a package manager). Some teams actually use this to deploy to production (continuous delivery), but even if you don't, you can still leverage this for deploying extra, non-production copies of the code. For some projects where I work, we have a copy for developers to test their code before making it available to QA, a copy for QA to test, and a more "stable" copy for demoing purposes.

The point is simply this: there are tasks you must periodically perform in the process of developing software besides just writing the code. By automating these tasks and having them run on a server, you get

  • Consistent process (You won't have Stan and Sally doing things different ways.)
  • Knowledge of processes recorded in code (Anyone who can read the scripts can learn the steps involved in deploying, instead of Sally being the only one who does it or knows how.)
  • Simpler duplication of processes (Simple to deploy multiple copies of the web site: you just provide a new configuration!)
  • More thorough testing (Bob only tested his page, but his changes broke Sally's page. Sally forgot to commit a file. Stan added a new dependency that has to be installed alongside the app but didn't realize it because it's installed automatically by the IDE. I've seen all of these in some form or another.)

And probably some other benefits that aren't even coming to mind.

  • Thank you for the answer. The examples are great. I wish I could vote more than one answer as accepted :-/ – Lord Loh. Feb 22 '16 at 2:11
  • @LordLoh. No worries. I'm just glad I could help. =) Thanks for letting me know. – jpmc26 Feb 22 '16 at 2:21
  • 1
    Upvoted, excellent answer. Like anything, if done poorly you might not reap the advertised benefits. E.G. consistency, process knowledge, simplicity may all suffer if you overbuild. So... evaluate your needs realistically and Godspeed! – brian_o Feb 23 '16 at 19:23

You might not need to compile the solutions, but CI can still help you by changing the config files/folder paths etc. and if you are in a team- promoting the changes to prod status and deploying them

Say you deploying your Python code to 5 different QA servers and need it pointing to different QA databases, and then once the automated test run (triggered by CI), promoting the build to production and deploying it there with appropriate config changes for every production server.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.