New features to protect your site from AI scrapers and other bots
New bot protection functionality with detection of AI scrapers, bot categories, and an open source list of bot identifiers.
Implementing security rule testing in Node.js by integrating Newman with your development workflow. Ensure your application functions the same in development and production.
Testing! It’s not a new concept in software development, but it’s mostly been missing from security tools.
How can you be confident that your rate limiting, bot detection, or validation rules work as expected as your code evolves? The traditional challenge has been that security tools often exist separately from the application, making testing cumbersome and risky.
If your security rules are implemented outside of your application, you need to build an entirely separate system for testing them. If they’re on the network layer, you have to send real traffic to trigger them, which often means you have to attack production infrastructure.
The developer security tooling we're building at Arcjet changes the game by unifying security and application logic. It runs consistently across development, CI/CD, and production environments, allowing you to integrate security rule testing directly into your functional test suite.
I’m sure many of you have flipped that security switch on a new tool, WAF, firewall, or other security system only to brick your production deployment! Not fun.
Untested security tools and rules can lead to:
Regular testing ensures your security rules remain effective and aligned with your application's behavior.
Arcjet is designed to run in every environment. Install the SDK into your application then use middleware or call protect()
in each route. The request is passed through our WebAssembly module for local analysis and our real-time decision API is used when we need to track state. Then within a few milliseconds you get a result that can be integrated into your application logic.
It’s the same process wherever your application runs. On a developer laptop. In CI/CD. In production. This means you can now include security rules as part of your functional test suite.
Testing security rules just means sending the right traffic to your Arcjet-protected application. How to test each rule depends on the rule type:
x-arcjet-suspicious: true
header will cause the 6th request to be denied. This simulates analysis of a client over multiple requests before it hits the suspicion threshold.User-Agent
header set to curl
and you should see a DENY
response.There are many tools that can send requests to web applications. The likes of k6 and Artillery can be used, but they are more designed for load testing. Instead, we recommend using Newman. Newman is a CLI that uses the popular Postman Collections format to define request templates, but can also be included as a Node.js library which makes it ideal for scripting test scenarios.
And if you don’t use Postman, it’s not required. Newman can be used independently.
This example shows the configuration of a fixed window rate limit with a maximum limit of 50 requests over a very short 3 second window:
import arcjet, { fixedWindow } from "@arcjet/next";
const aj = arcjet({
key: process.env.ARCJET_KEY,
rules: [
fixedWindow({
mode: "LIVE", // will block requests. Use "DRY_RUN" to log only
window: "3s", // 3 second fixed window
max: 50, // allow a maximum of 50 requests
}),
],
});
We could then test it with this Postman collection template JSON:
{
"variable": [{ "key": "baseUrl", "value": "http://localhost:8080" }],
"item": [
{
"name": "/api/high-rate-limit",
"item": [
{
"name": "Test high rate limit",
"request": {
"url": "{{baseUrl}}/api/high-rate-limit",
"header": [
{
"key": "Accept",
"value": "application/json"
}
],
"method": "GET",
"body": {},
"auth": null
},
"event": [
{
"listen": "test",
"script": {
"type": "text/javascript",
"exec": [
"pm.test('returns proper status based on iteration', () => pm.response.to.have.status(iteration < 50 ? 200 : 429))"
]
}
}
]
}
]
}
],
"event": []
}
Using the Newman CLI to execute the test, we would expect to be under the limit with a 200 response status for 50 iterations. The 51st iteration should then return a 429 response.
npx newman run tests/high-rate-limit.json -n 51
This works nicely from the terminal, but can also be converted into a test script using the standard Node.js test runner.
import { after, before, describe, test } from "node:test";
import assert from "node:assert";
import { fileURLToPath } from "node:url";
import { promisify } from "node:util";
import { run } from "newman";
// Promisify the `newman.run` API as `newmanRun` in the tests
const newmanRun = promisify(run);
describe("API Tests", async () => {
test("/api/high-rate-limit", async () => {
const summary = await newmanRun({
collection: fileURLToPath(
new URL("./high-rate-limit.json", import.meta.url),
),
iterationCount: 51, // 50 are allowed, so 51 trigger the rate limit
});
// The `summary` contains a lot of information that might be useful
// console.log(summary);
assert.strictEqual(
summary.run.failures.length,
0,
"expected suite to run without error",
);
});
});
Place this file in tests/api.test.js
alongside the high-rate-limit.json
file, then execute it with: node --test
This snippet assumes the application server is already running. You can see a full example on GitHub that includes starting the API server as part of the test suite.
By weaving security rule testing into your functional testing process, developers can deliver software that's not just functional, but also more secure. And avoids breaking production!
New bot protection functionality with detection of AI scrapers, bot categories, and an open source list of bot identifiers.
How to protect GraphQL backends using Arcjet. Implementing rate limiting and bot protection for Yoga + Next.js.
Detect, block, and redact PII locally without sending it to the cloud using Arcjet's sensitive information detection, plus the new integration with LangChain.
Get the full posts by email every week.