Submind YouTube summaries
Thumbnail for Security on Autopilot: Low-Touch Automated Security for Drupal Projects / Other / Nathan ter Bogt

Security on Autopilot: Low-Touch Automated Security for Drupal Projects / Other / Nathan ter Bogt

Watch on YouTube

Video summary

The presentation introduces a comprehensive strategy for achieving "security on autopilot" within Drupal projects and other applications by automating security testing to minimize manual overhead while maintaining high standards of safety. The speaker challenges common myths, such as the belief that small teams are not targets or that passing a single penetration test is sufficient, emphasizing instead that attackers utilize automation regardless of an organization's size. The core objective is to identify vulnerabilities in application code, dependencies, and runtime environments early in the development lifecycle before they reach production, thereby reducing the time and cost associated with fixing security incidents later on. Success in this model is defined by receiving automated notifications about specific issues within particular environments along with their risk levels, often resulting in pre-written pull requests that have already passed local tests, code quality checks, and functional validations. The technical approach relies on a three-layered static analysis framework compared to Formula 1 scrutineering processes where vehicles are inspected while stationary before hitting the track. The first layer focuses on application code using tools like PHPStan to detect issues such as poor error handling or direct database queries that could lead to SQL injection, ensuring these problems do not merge into the main branch without review. This is supported by AI-assisted code reviews and automated unit tests to catch architectural flaws early. The second layer manages dependencies through regular maintenance workflows using tools like Dependabot, which automatically generate pull requests for updates; a key tactic involves pinning problematic versions temporarily so that automation can continue updating other packages while the specific issue is resolved without breaking the build pipeline. The third and final critical layer addresses the runtime environment, acknowledging that even perfectly coded applications running on vulnerable servers or containers are not secure. The speaker highlights the necessity of scanning both development environments to prevent introducing new issues during builds and production environments where actual attacks occur. While a fast baseline scan using OWASP ZAP is run frequently against pull requests to check for obvious misconfigurations like missing security headers, a more thorough but slower full dynamic application security testing (DAST) scan is performed weekly on safe staging or QA clusters that mirror the production setup. This ensures that vulnerabilities such as SQL injection via forms or cross-site scripting are caught in an environment where data exists and can be exploited, without risking corruption of live customer sites. Ultimately, the goal is to create a seamless workflow where developers start their day by reviewing security reports rather than initiating new tests, allowing them to simply merge pre-validated pull requests that fix identified issues immediately. The speaker stresses that relying solely on scanning the main branch code is insufficient because production deployments often lag behind development updates; therefore, containers running in production must be scanned regularly using tools like Trivy for OS vulnerabilities and OWASP ZAP for application-level threats. By integrating these automated processes into GitHub Actions or similar CI/CD pipelines, organizations can ensure that security patches are applied quickly with minimal impact, keeping dependencies updated and the overall attack surface significantly reduced without requiring constant manual intervention from the development team.
Read the full video transcript
Kia ora. Uh good afternoon everyone. Uh welcome to my talk about security on autopilot uh and how we can set up automated security testing uh set it up once and use it going forward. Uh if that if you think that means that we don't need to do any work, then you're in the wrong talk. Uh I'm going to start with some security myths and why teams like to throw them around and the reasons that I completely disagree with them uh and let's just have a look. Uh we've all heard it, we'll get to it later. Be honest with yourself. You won't. You likely have put off your functional tests as well. Uh did you get around to writing your functional test? Uh it'll slow down delivery. It won't slow you down, you're just deferring the time investment. Uh doing things further down the development process is generally more time expensive and doing it when you have a security incident is definitely more time expensive. Uh we're too small to be a target. Nobody is too small. Attackers have automation too and the automation doesn't care how big you are. Uh and finally you passed a penetration test. That's great for today. Tomorrow there's another 10 CVEs. Uh so what do we want to do about it? We want to look at ways to automatically protect ourselves uh and respond to incidents as quickly as we can. So what we want to achieve? We want to quickly identify the issues in our application and our dependencies. And we want to keep our application dependencies up to date. Uh we want to pick up issues early in the development process so that they don't make it to production but just as importantly, we want to pick up pick up issues in our running environment. Uh what does success actually look like? That we're notified by an automated system that a security issue exists and it's in which environment and how long it's been there and the risk level of that incident. Uh fingers crossed, we've already had a pull request created by an automated system. Uh and it has already run all of the local tests, code quality, functional tests, etc. Uh and you're just going to have to look at merging it. Uh and we've limited Uh we've kept our application dependencies up to date, but that's to limit the footprint of a PR for a security fix. So, we want to know we have a security issue by scanning our application, not by an incident. We want to know well before any incident, and we want to know that it's fixed and available and ready um before it even gets to that. Uh I'm going to refer to Formula 1 for a little bit uh to help give a bit of context. But, in Formula 1, the FIA has a process called scrutineering. The car's placed in a purpose-built booth and 3D laser scanned and lidar is used to see if the car dimensions are to spec. Uh they check the weight of the car, and they check engine engine displacement and things like that, and make sure it's all up to code. And they do these checks while the car's static. It's not moving. That's what SAST is. So, we are doing all these tests for our application code, our dependencies, and our runtime environment while not running the application. Uh we're specifically scanning the the assets we have and not doing a dynamic test against the application. Uh we have three different layers of that test of that testing. Uh the first is the application code, then which is our code, there's the application dependencies, and then there's the environment that we put our application onto. Uh the application code. The application code is your code. We're assessing your application's code for possible issues. Our automated tests, uh tooling like PHP Stan, can pick up things like poor error handling. Uh and that can stop an attack before it becomes an issue. An example would be say you don't respond to a exception properly in session authentication. Uh additionally, if you see a common issue in your team, uh you can automate the detection of that to save on your code reviews and uh just the time taken to get code to production. Uh an example of that is your team uses a lot of direct query APIs in database for Drupal, but you should really be using select and update so that you don't have SQL injection attacks. Uh I consider PHP Stan to be foundational and the first thing that you need to implement it in an automated security testing setting. Uh the reason I say that is as we start to automate it dependency updates, uh and application like runtime updates, PHP Stan can pick up things like function definitions changing but or the function used to throw an exception instead of a boolean, all that stuff. So, you're getting that feedback as part of your build system and your workflows. Uh, we should run PHP Stan on every single pull request. Uh, as I said, it's picking up issues early uh, and making sure they don't make it to production. Uh, uh, but also on integrations to your main branch, so that you're testing that as lots of work is happening. And while this is not really a CI CD task, a code review is also an essential part of the application code checking. Uh, we've had great success at automating parts of the code review using Copilot and Claude uh, to help reduce the load on our reviewers, but not remove the load of our reviewers. Uh, allowing the humans to pick up architectural issues that could create something like a DDoS vector uh, or catch edge cases for like a login bypass. Uh, you can automate it, use AI, but you still need your humans to do that overall architecture. Uh, and I will put in here, you also need automated unit and functional tests, uh, but that's a whole different talk. Uh, the next level is your application dependencies. Uh, we have tools like Dependabot that help you manage your dependencies, uh, but this is about protecting yourself against someone else's code. Uh, this is scanning your dependencies, doing maintenance and management of updating them. Uh, regular maintenance PRs that upgrade your dependencies are important because if it doesn't update cleanly, you have time to fix it. You don't want to do that when you have a security incident and you have to upgrade 200 packages and all their issues to fix one security bug. Uh, something that works for me, uh, and just a little win is that if I have a bug in a specific dependency update then I'll pin that version I'll commit the chan- changes and create a task, like a Jira ticket, for unpinning it. The reason for that is if you do that, the automation keeps going. All your other dependencies keep upgrading, you keep getting pull requests, things aren't breaking and you have time to come back, fix the pin version, and put it up to the whatever you need to. Uh we should run the maintenance workflow against your main branch at least once a week. Uh but in our case we run it on like what might say Oh, that one's daily. Uh but on some projects we run it weekly, but we'll run it on Wednesday morning so that we have time to do it during the week. Uh, another thing on here, this is specific to Dependabot. But this is a new feature they added in, cool down default days. Uh, that'll protect you from a zero-day exploit. It'll only give you updates for something that's at least a day old. Uh tools like Dependabot, uh, and Renovate, and there's a couple of others uh, will send you a pull request when there's a security issue. So, this this is dependency maintenance, but when you actually have a security issue, you'll get that pull request within a couple of hours of when that's released. Uh because we've been taught on top of all the maintenance upgrades and making sure we merge them and looking after all our dependencies, it should be a small, easy, low-impact task to review that security update and merge it. Uh the tools so far go hand in hand. Without the maintenance pull requests, without PHP Stan checking our code, and without a solid unit test suite, security PRs are going to take a long a lot longer to test and a lot longer to confidently merge. The third stage of our static testing is the runtime environment. So, your application can be super secure. You've done everything so far. You've done all your dependency management. You've done all your PHP Stan, etc. But, you put it on a Linux kernel with a TCP vulnerability. And that's taking your whole site out. Uh you're no better off if you don't also test this layer of your code. So, here in our case, we're using tools like Trivy. Uh that will take a Docker container and scan that for all installed versions on that container and give you a report of, you know, OpenSSL has an issue, Engine X has an issue, all that kind of stuff. Uh it should be run again for all your pull requests and all your merges to the main branch, same as what we're doing for everything else. Uh if available to you, depending what tool set you're using, uh GitHub in this case does it. Uh a lot of these static tools can export a file called a SARIF file. And that's a static analysis results interchange format. Uh I don't remember that. I call it SARIF. Uh but then you can use UIs like GitHub security scanning to inject all those SARIF and get a report. Uh this is a report from an example project we have. But more importantly, you do this for 10 projects, and then there's a dashboard higher than that where you can check how all your projects are going. And here's the kicker. Unless you're a rockstar doing continuous deployment, a lot of the static security testing needs to be done twice. You need to ensure that you scan your development environments as well as your deployed environments. Uh we definitely don't want to introduce a issue through our development, uh so that we need to do those on every pull request. But if you only release every month or so, then what happens in your main branch doesn't matter. Uh you need to know you have a major security issue on your production server ASAP. Uh so your production site is where the attacks are most likely to happen. It's the environment that has the data to exploit, and it's the environment where your reputation is most at risk. So you need to pull down your production environment, and you need to run all of the same testing suite. Now, back to Formula 1. So let's say our car passed all the scrutinizing, weight checks, engine checks, etc. But, we take the car out on the track and we fail at 300 km an hour. Uh we passed the weight test because we didn't use enough carbon fiber to cope with the forces on our wings. They fell off and the car fell apart. That's dynamic application security testing. So, this gap is filled by standing up your environment, running it, and then setting some other security tools onto it. Uh it's testing the run running application for security issues, things that our static test can't pick up. It's issues like missing content security policy headers, insecure TLS supported versions, or worse, SQL injection issues by a forms or URL query parameters. Uh if these sorts of things are exploited, uh it'll allow an attacker to wipe your database or export all the data out of it. So, we have a couple of tools for these. Well, one tool, but it's got a couple of different versions. So, we'll go through that. Uh OWASP ZAP is a baseline tool that can we can leverage to find these types of issues. Uh it targets the OWASP top 10. Uh and if you haven't looked at them recently, then I suggest you have a look at that URL. Uh they change every few years, and they change the top 10 based on thousands of recommendations from different security companies as to what people being exploited by. Uh so, to run this baseline, uh you need a deployed working site. It crawls the site for a limited time. Uh generally a minute, but you can change it if you want to. Uh and it will report on all sorts of things that can be improved. The baseline scan is safe to run against any endpoint as it specifically won't try to destroy your site. Uh we again run this test on every single pull request and every merge to main. Uh once it's deployed, uh just to test that we haven't injected any new issues into our products. Uh if OWASP ZAP was the um one that's safe to run, then this is the unforgiving big brother. Uh you pass it a seed URL. It will crawl the entire site until there are no other URLs to find. Then it will actively assess your pages for forms and things, and then attack with SQL injection, cross-site scripting, all that kind of stuff. Uh if you have a vulnerability, it will corrupt your website. I can tell you that from experience. Uh and it's considered unsafe to run on any production site for obvious reasons. Probably your QA site, too, if you want to get work done that day. Uh but it is worth calling out that the full scan is slow. It takes a while to set up an environment that you can scan, like a safe environment that you are allowed to scan. Uh and we only run it about once a week. And we run it in completely separate different workflow, nothing to do with our pull requests and main branch. Uh we feed any issues that it comes up with back into our products through just general Jira tickets. So, all of these things can be set up with GitHub actions and workflows. So, you can have pull requests running all PHP stand and Trivy, all those sorts of things. Uh and then you can have I don't know, wherever you run your functional tests against your deployed environments, you can have OS running and making sure CSP headers are all working. Uh but we need all of those underlying layers, like functional unit tests or functional tests, unit tests. Uh PHP stand again. We need all of that working in order for this to be fully automated. Uh what you don't want is Dependabot sending you a security PR and you don't have any tests. You don't know whether it's actually going to work when you merge it. Uh I've gone a bit faster than I thought. But I'll go over these and then I will take questions if they'll I'll show you a demo of the OS report and then we'll do some questions. Um but SAST is a security test of your code, your dependencies, and your application runtime environment. Its purpose is mostly to let you know your application was safe. Uh well, what is as safe yesterday as it is today? The CVEs change every single day, and if you're not scanning often enough, you won't know that you have an issue. Uh DAST, however, is a security test of your running application. Mostly to ensure you're protecting yourself from SQL injection attacks, bad security headers, misconfiguration of your environments, etc. They cover two different security problems and they largely don't overlap. You need both. Uh we don't want to write code that creates a new security issue and that's why we run all those workflows for every pull request, every main branch. Uh but we don't want any issues in our production environments, either. So, we need to run them. Pull down your containers that you're actually running, run the same test suites against them. Uh keep on top of your maintenance pull requests to limit the splash zone of a security pull request. Uh a single package with a single patch version is a lot easier than 200 packages with major versions. Uh finally, automate everything. When you the goal is when you start work in the morning, you do a quick check of the security reports. Hopefully, you already have a pull request available, the test suite has already run, and you have to click the merge button. Finally, that URL there, a lot of these techniques are live and running on that environment. Uh so, you can pull down that repository, have a look at see what's in there, um and uh that'll continue to evolve. This example project is actually the test Drupal project that we run on our QA clusters. Uh my name's Nathan Taber, I'm a sysops engineer at Previous Next and Skipper. Uh as Vladimir said, I've been a Drupal developer since Drupal 4. I looked up how long that was and I decided to say Drupal 4. Uh I've been living in Auckland now for a couple of years. Uh and Skipper Hosting is launching in New Zealand. Uh if you think of No, any questions? Now, I will quickly show you that example project is particularly bad at the moment. Uh and here's the report to prove it. So, this is an OWASP I think it's a baseline report. I don't even think it's the full report. Uh but this is what you get out of an OWASP scan. Uh you get your high, medium, and lows. You get the reason and what the issues were. But then if we scroll down here, we get this massive report. Uh this is what it comes up with in in a minute. You can imagine what a full scan against your site is. Uh So, it has found that there's a dangerous JavaScript function running in your code with a dynamic test. And it'll tell you the exact URLs that it found it. Uh feature policy is not good enough. Like all that kind of stuff. Uh so, if you just run that uh and then go through and create tickets for whatever you think is important, uh you'll be better than 90% of the people anyway. >> Did you say yeah? >> So, yeah, it depends on the project. So, if it's an example Drupal project that we just have as our testing suite, then obviously weekly, fortnightly is fine. Um but we do have a couple of projects where we do need to know daily. Uh so, we'll run those daily. Um and it's important to say that that daily weekly is only for maintenance pull requests. The security pull request from Dependabot is going to come no matter what. >> Yeah. Is it? That's the style of it. >> Yeah, okay. >> It's getting >> Yeah. Uh so, as I said, um we try to do really quick scans for pull requests and merges domain. And the reason for that is to get really fast feedback to the developers. Oh, there was a bug. I'll fix that. Which is why we do the baseline scan for 1 minute. We just want to know did we put something really obvious in that we shouldn't have done? So, we can get that result back. Uh the expensive scan, like the full scan with the whole environment setup, I guess you could Uh, we generally do it weekly, but you could consult with your client and say, "It's going to cost about $4 in workflow." How often? Like, where's your risk level? >> Yeah, yeah. >> Yeah. >> How do you >> Yeah, and and I do see a lot of people set up all of this type of testing and workflows and everything, and they just do it against their main branch. Like, it is really I can't stress how important it is to run the test against your actual production working code. We have code, well, there is client code in a cluster somewhere that was last deployed 18 months ago. Like, the security doing the security on the latest main branch, who cares? Yeah, so there was um, a talk yesterday uh, on the OSB scanner. Uh, so that you can actually run the OSB scanner in your container that you have deployed on production, if you want. Um, and Renovate and Sneak can target within a file system. It doesn't have to be the main branch. You can say, "Mount the file system, scan that, and get the results back." Um so, there is a couple of different ways to do it. Uh but, at least for our clients, most of them are doing deployments every 2 weeks or so. So, as long as we scan the container for Nginx, OpenSSL, etc., the actual application ones are getting fixed fairly quickly.