Using Wasm requires bindings to cross between host and guest. Working these by hand is fine for 1 language, but what about 2, or 5, or 10? Then you get into the world of automated codegen and have to ask: should code be generated to feel more natural to the language or it can be a more direct mapping to the Component Model types. Neither option fits 100% of use cases so it is up to the tool authors to decide which makes the most sense. Developers may struggle with non-idiomatic patterns, leading to verbose, less maintainable code. Using established conventions makes the code feel more familiar, but does require some additional effort to implement. We decided to take the idiomatic path to minimize friction and make it easier for our team so we know what to expect when moving around the codebase.
About us
Arcjet helps developers protect their apps in just a few lines of code. Bot detection. Rate limiting. Email validation. Attack protection. Data redaction. A developer-first approach to security.
- Website
-
https://arcjet.com
External link for Arcjet
- Industry
- Software Development
- Company size
- 2-10 employees
- Headquarters
- San Francisco, California
- Type
- Privately Held
- Founded
- 2023
- Specialties
- devtools and security
Locations
-
Primary
San Francisco, California, US
Employees at Arcjet
Updates
-
Introducing Nosecone: an open source library to set security headers like Content Security Policy (CSP) and HTTP Strict Transport Security (HSTS) on Next.js, SvelteKit, and other JavaScript frameworks using Bun, Deno, or Node.js. Whether you’re adapting to the stricter security header requirements of PCI DSS 4.0 which comes into force in 2025 or are simply looking to enhance your app’s security, Nosecone offers: - A type-safe API with pragmatic defaults. - Middleware adapters for Next.js. - Config hooks for SvelteKit. - Easy integration with web servers in Bun, Deno, and Node.js.
-
This is how we used Astro's Starlight framework to build our documentation with support for framework switching, a custom sidebar, and a custom table of contents for improved SEO and a better user experience. Documentation is the product and we spend a lot of time on it! We initially started with Nextra, a docs framework for Next.js, however, we found it to be too inflexible and difficult to customize. After some evaluation, we turned to Starlight: a needs-no-presentation, content-driven Astro docs framework. This has been a very flexible choice with virtually no friction in adoption, serving us well until recently. However, as our SDK started to add support for different frameworks, developing its functionality and increasing features, we realized that the docs structure was becoming defective and painful to work with. Read more on our blog (link in comments)!
-
Today we're announcing support for NestJS and Remix! We started with the Next.js framework which used our underlying Node.js SDK. The core functionality lives in the runtime SDK, which we extend with the framework specific adapters to make them feel native. The result is that using the Arcjet [Next.js | SvelteKit | Node.js | ...] SDK feels like programming against a native [Next.js | SvelteKit | Node.js | ...] API. If we don't have a framework SDK you can still use the runtime language SDK, but it requires a bit more work. So today we're announcing support for both NestJS and Remix which now have their own native Arcjet adapters! That brings us support for Bun, Deno, Node.js, Express, Hono, Next.js, NestJS, Remix, and SvelteKit. More on the way!
-
The elegant design of server actions hides the implementation details of handling a normal API request. This makes it easier to create simple functions for common actions like form submissions, but lulls developers into a false sense of security. All server actions are public HTTP endpoints, which means anyone can make calls to them. You should treat them like any other API endpoint and ensure you handle things like authentication and validation. Next.js 15 introduced unique, non-deterministic ID references for server actions to make it more difficult to locate and reference the APIs. However, this is just security by obscurity and the endpoint can still be found within the client code or when triggering a request to the server action. Unused server actions will not have their IDs exposed to the client-side JavaScript bundle. However, if a user were to get the handle to the ID of an in-use action, they could still be invoked with any arguments. Further, server actions defined in React components are generated as closures, meaning they have access to the parent scope. Data is sent from the client to the server which could expose sensitive information - this is encrypted, but data is still sent unless you use the React Taint APIs. This also has implications for self-hosting Next.js because the generated encryption keys will be different on each server. You will need to handle syncing the encryption keys to ensure requests that round-robin to different servers work correctly. POST APIs have built-in protection from CSRF attacks in modern browsers so server actions inherit this by default. However, it is still possible to bypass those protections. To fully protect server actions against CSRF you need to set the experimental allowedOriginssetting in your Next.js config. These are the architectural security implications. Once you've considered these, you then need to implement usual API security protections.
-
After a short internal Rust vs Go bake off, we chose Go + Gin to reimplement our REST API. Our low-latency gRPC API is also implemented in Go, which gets called from our JS SDK. We're still using Rust to compile to Wasm of course because we don't want to bundle the Go runtime with the GC. Picking the best tool for the job 💪
-
Implementing request parsers in Rust allows us to take advantage of its inherent memory safety, correctness, and performance. That's why we used Nom to build our email validation. Nom is a parser combinator library written in Rust designed as toolchain for building "safe parsers without compromising the speed or memory consumption". Its design focuses on zero-copy parsing (memory-efficient data interpretation without allocations), using Rust's streaming capabilities, and bit-level parsing support. This makes it highly efficient and versatile. Creating an email parser requires combining local part parsing with domain parsing to ensure we validate the syntax against the RFCs...but of course just following the RFC doesn't quite work in the real world!
-
Arcjet reposted this
👱PII Redaction Lots of people have asked how to do PII redaction Detect, block, and redact PII locally without sending it to the cloud using Arcjet's sensitive information detection. Now integrated with LangChain https://lnkd.in/e7zmdkeS
-
How we achieve our 25ms p95 response time SLA? 1. Local-first security The first step to fast response times is processing as much as possible locally. Although your interaction with the Arcjet SDK is in JS, most of the analysis happens inside a WebAssembly module. We bundle this with the SDK, and it runs in-process without requiring any additional software like Redis or an agent. 2. A low-latency gRPC API in every cloud region Not everything can be analyzed locally. Rate limits need to be tracked across requests, and we operate an IP reputation database. This is all handled via our API. If a decision can’t be taken locally, then our API will augment the analysis with a final decision. As this blocks requests to your application, we set ourselves a p95 latency goal of 20ms, with an additional few millisecond allowance for network latency. This means it needs to run in the same cloud region - we’re currently deployed to 22 different regions. 3. Persistent HTTP/2 connections The slowest part of making a request is often establishing the initial connection. A normal TCP handshake requires 1 round trip, and the TLS handshake requires another 2. If a round trip takes just 1 ms, then that’s easily 3 ms taken up just opening the connection. Then the API request requires another round trip. A few months ago, we introduced support for multiplexing requests over a persistent HTTP/2 connection. When the Arcjet SDK is instantiated, we open a connection to our API and then keep that connection open over multiple requests. 4. Smart caching If a client request is denied, then the chances are their next request should probably also be denied, but it depends on which rule caused the deny decision. This is where our smart caching comes in. When an email verification request results in a deny, that should not be cached because it may be because the user made a typo. Their next request should be freshly re-evaluated. But if it’s a rate limit rule that denies a request, we can look at the configuration to determine whether another request is going to result in another deny. Not only do we consider whether they are already over the rate limit, the time to cache the result is determined by the rate limit configuration. If the limit applies for a fixed window over the next 30 seconds, then we’ll cache for 30 seconds. Results The result is our p95 API response time of around 25ms, which is within our goal range of 20-30ms. Our p50 is around 4ms, but we pay more attention to the outliers revealed by the p95 because those are what cause real user experience degradation.