Skip to content

Secure at every step: Putting DevSecOps into practice with code scanning

Integrating static analysis security testing into the developer workflow is hard. We discuss the challenges and how to overcome them

Secure at every step: Putting DevSecOps into practice with code scanning

If you’ve read Maya’s post on DevSecOps, shifting left, and GitOps you might be wondering “how do I implement these security principles in practice?” Let’s dive deeper with a practical example: integrating static analysis into the developer workflow.

What is static analysis, and why would you integrate it into the developer workflow?

Static analysis security testing (SAST) analyzes the code you and your team have written for vulnerabilities. Also known as code scanning, it works by transforming your code into a queryable format and then looking for vulnerable patterns in it, like sending unsanitized user data to a database call. You can think of static analysis tools as souped-up linters (although doing so is doing them a disservice—modeling data flows across files and function boundaries is hard).

Static analysis security testing tends to happen late in the development cycle, as part of a security review. Moving that testing into the main developer workflow, so that every pull request is analyzed with static analysis, is a perfect example of “shifting security left.”

Why integrate static analysis into the developer workflow? For all the reasons laid out in Maya’s post on the DevSecOps approach. Integrated well, it means security issues are found during everyday code review and can be fixed before getting close to production.

Challenges shifting static analysis left, and how to solve them

If integrating static analysis into the developer workflow is such a great idea, why isn’t everyone doing it? Mainly because it’s hard, and because done wrong it can be harmful. Let’s dig into some of the challenges, and how to fix them.

To be integrated into the pull request workflow, a tool needs to be fast. Introducing a slow static analysis tool increases the time your engineering team spends waiting for CI, which is a surefire way to burn developer productivity. Context switching will go up as happiness and output go down. To avoid that fate (or the more likely one that the project to shift left gets aborted), monitor the impact of new analysis to your CI time carefully, and move slow queries or tools out of the main CI loop and onto a (regular!) schedule.

Tools in the pull request workflow also need to be precise. Introducing a noisy static analysis tool is a quick way to train an engineering team to ignore automated security findings completely. Industry best practice is to target a false positive rate of 10 percent or lower for results shown in pull requests, but achieving such a low false positive rate is hard. The solution? Don’t  shift all security scanning left—noisier checks can continue to be run and reviewed by the security team, while high-precision ones are moved into the developer workflow. A great static analysis tool should also make it easy to iteratively improve its queries.

Finally, tools integrated into the pull request workflow need to be designed for developers to review, not security teams. Static analysis security testing can surface results but, at least for now, it takes humans to fix them. Only new findings, caused by the changes proposed in the pull request, should be shown in the context of a pull request review. Each result should be described clearly enough for a developer new to security to understand why it may be important. And if a result is dismissed as a false positive it should be easy for the security team to later understand why.

Defining static analysis configuration as code

Maya’s post also talked about the benefits of defining configuration as code, particularly when stored in a Git repository. Let’s take static analysis as a practical example.

With any static analysis tool, there’s configuration required. You need to specify when to run the analysis (every push / every pull request / every day), how to analyze the project (for compiled languages this often requires details of how to build it), and what analysis to run (which queries, any paths to ignore, etc.).

A file committed to the repository being analyzed is the ideal place to store that configuration. It’s immediately visible for anyone with access to the repository and has the same version control and change management as the software being scanned.

GitHub code scanning

With all of the above in mind, we’ve built GitHub code scanning to help you shift security left.

Code scanning puts the developer experience first at every step. The static analysis engine at its core, CodeQL, is fast and powerful—capable of finding real security issues without the noise. The queries it runs are precise, configurable, and are constantly being improved by the open source community. Results are displayed in in-line pull request comments, with detailed descriptions and remediation advice. All configuration happens as code in a GitHub Actions workflow file.

Enable code scanning in your repository 

Looking for more easy ways to keep your code secure? Stay tuned for upcoming posts in this series or check out our security ebook.

Explore more from GitHub



Secure platform, secure data. Everything you need to make security your #1.
GitHub Universe 2024

GitHub Universe 2024

Get tickets to the 10th anniversary of our global developer event on AI, DevEx, and security.
GitHub Copilot

GitHub Copilot

Don't fly solo. Try 30 days for free.
Work at GitHub!

Work at GitHub!

Check out our current job openings.