The core to any container security effort is testing the code and supplementary components which will execute within containers, and verifying that everything conforms to security and operational practices. One of the vital progresses over the past year or so is the initiation of security features for the software supply chain, from the packaging of container and runtime environments including CoreOS’s Rocket, Docker, OpenShift, and so on.
Many third-party vendors are helping to validate container content, both before and after deployment. All solution focuses on a bit different threats to container construction. For example, Docker offers tools to certify that a container has gone through your process without modification, using container repositories and digital signatures. Third-party tools focus on security advantages outside what runtime environment providers put forward, like examining commonly used open-source libraries for known flaws.
Digital signing services and process controls are important to verify the chain of custody and making-of-material bills based on known trusts. Also, you may need more than what is packaged with your base container management platform. It would be better to consider a third party to help harden your container inputs, analyze static code, analyze resource usage, analyze library composition, and check for known malware signatures.
Some risks won’t be caught by your base platform.
Container Validation and Security Testing
- Runtime User Credentials:
It is not recommended to run container processes as `root`, because this will provide attackers quite access to the underlying kernel and a clear road to attack other containers and the Docker engine itself. It would be better to use specific user ID mappings with limited permissions for every class of container. We know roles and permissions change over time and it requires ongoing work to keep kernel views up to date. User segregation provides a failsafe to restrict access to OS resources and virtualization features underlying the container engine.
- Security Unit Tests:
One of the great ways to run focused test cases against specific modules of code are Unit tests – typically created as your development teams find security and other bugs without needing to build the entire product every time. They cover testing of known attacks like XSS and SQLi against test systems. As the body of tests grows over time it provides an expanding regression test-bed to ensure that vulnerabilities do not creep back in. Even though most are moving to micro-services, fully supported by containers, they find it easier to run these tests earlier in the cycle. It is recommended to have unit tests somewhere in the build process to help validate the code in containers is secure.
- Code Analysis:
Several third-party products execute automated binary and white box testing, rejecting builds when critical issues are tracked down. Also, there are different new tools available as plugins to common IDE where code is checked for security issues before check-in. It is recommended to implement a few forms of code scanning to verify the code you build into containers is secure. Most of the newer tools give full RESTful API integration within the software delivery pipeline. All these tests generally take a bit longer to run but still fit within a CI/CD deployment framework.
- Composition Analysis:
Another security method is to check libraries and supporting source code against the CVE database to decide whether you are using vulnerable code. Docker and other third parties provide tools for checking common libraries against the CVE database that can be integrated into your build pipeline. As containers are built in layers, including many open source libraries and tools along with proprietary application code. Developers are not typically security experts, and an independent checker to validate components of your container stack is both simple and essential. This is because new vulnerabilities are discovered in common open-source libraries every week.
Before deployment, there are several tricks for securing containers by ensuring what you use is free of known vulnerabilities. This type of hardening is the same as OS hardening, that is, libraries and unneeded packages removals reduce the attack surface. There are different ways to inspect for unused items in a container and one can work with the development team to confirm and eliminate unneeded items.
A ‘lean base image’ approach to only keep the bare minimum of what is needed for the application to run, which you can enforce via manual reviews of through build scripts, helps reduce the attack surface. Another technique is to check for hard-coded keys, passwords, and other sensitive items in the container. These breadcrumbs make things simple for developers but may help the attackers even more. Some organizations use manual scanning for the same, while others leverage security tools to automate it.
Container Signing and Chain of Custody:
Make sure that the entire process was followed, and that nowhere along the way did a well-intentioned developer subvert the process with untested code. This can be achieved by creating a cryptographic digest of all image contents, and then track it through your container lifecycle to ensure that no unapproved images run in your environment.
Digests and digital fingerprints can help you identify code modifications and detect where each container came from. A few container management platforms provide tools to digitally fingerprint code at every phase of the development process, alongside tools to validate the signature chain. But these capabilities are never used, and platforms like Docker may only optionally produce signatures. Each code should be checked before being placed into a container library or registry, signing images and code modules occurs during building.
You have to create particular keys for every phase of the build, sign code snippets on test completion and before code is sent on to the further step in the process, and keep these keys secured so offenders cannot create their own trusted code signatures. This provides some assurance that your vetting process proceeded as intended.