Experience in implementing AppSec/DevSecOps practices

Development processes must be built to ensure a predictable level of product security at the output. It was with this idea that we began to modernize our internal processes at "LANIT - BPM".

We conducted a study of global security practices, which are often combined under the terms AppSec (application security) and DevSecOps (development, security, and operations). It was important for us that security is required not only when writing server code. The front end, infrastructure, build and deployment processes can also be vulnerable. Therefore, we paid attention to all these aspects. In this and subsequent articles, we will talk about our most interesting findings.

The first aspect is the quality check of the dependencies used. We studied popular solutions on the market: Dependency-Track, Mend, Snyk, Black Duck, Sonatype Lifecycle, JFrog Xray. Each of these tools offers a set of functions for detecting vulnerabilities, integration with CI/CD, but most of them are commercial. We chose Dependency-Track from OWASP. This is a free open-source solution that covers all our requests.

Several articles have already been written about it, for example, here. Therefore, we will try to highlight the most interesting nuances we discovered during the implementation.

Experience in implementing AppSec/DevSecOps practices in a large company Integration of security tools into the

Briefly about the principle of operation

Without going into technical details, which can be found in the official documentation, the general principle of Dependency-Track operation looks as follows.

  1. Collection of dependency information. The tool collects data on all the dependencies used in the project, including frontend, backend, and any other components where there are dependencies.

  2. Centralized storage and visualization. The collected data is sent to a centralized server where it is visualized in a user-friendly interface. This allows the team to get a clear view of the security status of the dependencies, manage risks, and make informed decisions about updating or replacing them.

  3. Vulnerability database scanning. After collecting the information, Dependency-Track checks all discovered dependencies against the vulnerability database to identify potential threats. The tool analyzes the dependencies' compliance with known vulnerabilities, their criticality, and impact on the project.

Connecting to the backend

We started with the backend in Java. Integration into the project is quite simple. There is a maven plugin for collecting dependency information in CycloneDX format with good documentation.

Connecting the backend


    
        
            org.cyclonedx
            cyclonedx-maven-plugin
            ${cyclonedx-maven-plugin.version}
            
                
                    package
                    
                        makeAggregateBom
                    
                
            
        
    

As a result of its work, files in the special SBOM format are created with a list of all the dependencies used in the project.

Next, this file should be uploaded to the Dependency-Track server, which is deployed independently and contains a beautiful UI for visualization. We also had no problems with its deployment.

Connecting to the frontend

There is also a ready-made plugin for the frontend. Building and publishing dependencies is done in two commands. Super simple.

sh 'npx @cyclonedx/cyclonedx-npm --output-file bom.json --spec-version 1.5'
dependencyTrackPublisher artifact: 'bom.json', autoCreateProjects: true, projectName: 'project-name', projectVersion: "1", synchronous: true

Connecting to the pipeline

We wanted the dependency information to be collected and published to the server with each project build, so we integrated this step into the CI/CD pipeline using the Jenkins plugin.

The plugin easily integrates with Dependency-Track and has several convenient features.

The first good news was that the plugin allows blocking the build depending on the vulnerability database analysis result. Each of our teams can set a threshold after which the build will fail according to their own policies and desired security level.

Another pleasant moment is that you can track the dynamics of the project. Team leads are satisfied.

Hidden pitfalls

When implementing in real projects, we encountered a number of nuances that may affect the efficiency and convenience of working with the tool.

Local build

For many developers, it is critically important to detect vulnerable dependencies at the earliest stage, even during the local build, rather than on the CI/CD pipeline. However, there was no built-in mechanism for this in Dependency-Track.

Solution Options

  1. Publishing a local build to the server and manual analysis through the UI. You can upload the BOM (Bill of Materials) from the local build to Dependency-Track and check for vulnerabilities manually through the web interface. However, this approach is inconvenient and labor-intensive, especially for frequent checks during local development.

  2. Using Dependency-Check. This is a separate library from OWASP that can be integrated into the build process. It can block the build when vulnerable dependencies are detected. You can configure it to run through Maven profiles so that the check is only performed during local runs, without affecting CI/CD. Dependency-Check uses the same vulnerability database as Dependency-Track, making this option suitable for early problem detection.

  3. Using a special Maven plugin. It sends the collected dependencies to the server and waits for the analysis results. This option is impractical as it either overwrites the main project's data or requires creating separate projects for the user, which is extremely inconvenient. Branch support within a single project is not yet provided.

We decided to sacrifice the ability to check dependencies locally. For us, the main priority was the quality of builds on the pipeline.

Trust in the Vulnerability Database

The main source of information about vulnerabilities is the NVD (National Vulnerability Database), which is maintained by the National Institute of Standards and Technology (NIST) in the USA. Using this database, despite its authority and reliability, may carry certain risks.

  • What if access to the database is closed? Interrupting the connection with NVD can affect the timeliness of receiving vulnerability data.

  • What if the integrity of the database is compromised? Possible errors or data manipulation can reduce trust in the security system.

However, Dependency-Track has features that help minimize these risks.

  • Local replica of the vulnerability database. Dependency-Track creates its own copy of the database and synchronizes it as much as possible, allowing it to work autonomously without a constant connection to NVD. This is critical to ensuring process resilience even when the connection to the external source is lost. The tool also allows the use of mirrors instead of the original database.

  • Managing the vulnerability list through the UI. The Dependency-Track interface allows you to manually manage vulnerability lists, adjust them, add or exclude items at your discretion. This gives the team the ability to flexibly respond to changing conditions and keep the data up to date.

You can manually expand the list of vulnerable dependencies. Or use a ready-made one compiled by local companies. For example, there is a threat database from FSTEC.

We decided to test the aforementioned database to expand the list of vulnerabilities in Dependency-Track and encountered a number of difficulties. Below are the main conclusions we made.

  • Format incompatibility. The FSTEC database does not support the CVE format, so the data needs to be manually converted before integration with Dependency-Track. This requires significant time and creates additional complexity when updating data.

  • Overlaps with CVE. Often, entries from the FSTEC database refer to existing CVEs, but are not full-fledged vulnerabilities for the project code themselves. This makes them more useful for identifying vulnerable applications and systems on workstations, rather than for direct dependency analysis during development.

  • If desired, an entry from FSTEC can be manually added to Dependency-Track. Despite the inconveniences associated with format conversion, FSTEC entries can be transferred to a local Dependency-Track server. This allows expanding the project's vulnerability database, taking into account specific threats that are not covered by international sources.

  • If you really want to, you can even automate this process and populate the database directly, bypassing the UI.

False Positive Management

Dependency-Track not only allows adding new vulnerabilities but also provides tools for managing false positives. This is especially useful when working with large amounts of data, where some vulnerabilities may be mistakenly marked as critical.

  • Filtering and setting exceptions. Using the interface, you can exclude false positives, add comments and justifications, which allows you to keep the list of current vulnerabilities under control.

  • Threat prioritization. The system allows you to set priorities and configure notifications for the most critical vulnerabilities, focusing on those that pose the greatest threat to the project.

Access separation by projects

Another nuance of using Dependency-Track is the ability to hide project analysis results from other teams.

For some projects, it is extremely important not to spread information about vulnerabilities outside the team. Previously, Dependency-Track did not have the ability to separate access to analysis results. However, in the latest versions, this feature has appeared in beta mode.

There is also integration with LDAP/AD, which means you can use the organization's existing approach to authorization. SSO is supported using OpenID. However, authentication is not without user participation. Instead of a username and password, you need to click the OpenID button.

Pilot results

Pilot implementation of Dependency-Track has shown that the use of vulnerable dependencies is a common problem faced by almost all projects, especially in the context of active use of open-source libraries. Without specialized tools like Dependency-Track, developers often do not realize the existence of this problem, and vulnerabilities can go unnoticed throughout the entire product lifecycle.

Integration of Dependency-Track into the development process was quick and without much difficulty. The tool easily integrated into existing pipelines and started delivering results almost immediately after setup. The team received timely notifications about identified vulnerabilities and outdated versions.

In addition to vulnerability analysis, the use of Dependency-Track provided an additional advantage — the ability to automatically analyze the licenses of the libraries and components used. This aspect is also important for our projects, as it allows us to monitor license compliance with internal requirements and reduce the risk of intellectual property violations.

Thus, the implementation of Dependency-Track not only improved dependency security control but also allowed for a comprehensive approach to managing risks associated with the use of third-party code and licenses. This is an absolute must-have for every project where you are concerned about product security.

Comments