Seamless k6.io Performance Testing in Scala Projects Using Scala.js
Michał Wiącek
Software Engineer
Published: Jan 20, 2026|22 min read22 minutes read
Modern systems rarely fail because of a single bug. More often, they degrade under real-world pressure: sudden traffic spikes, chatty cross-service calls, slow leaks that only surface after hours of load. Performance issues now emerge continuously in production, not during a dedicated test phase. Cloud environments and SRE-centric observability pushed load validation out of the controlled lab and into the delivery pipeline. Relying on auto-scaling and dashboards means discovering problems only once they are already impacting users in production.
K6 addresses part of these problems by making performance test code: versioned, automated, and integrated directly into CI. But it is a JavaScript-only scripting model. It is misaligned with teams that are building distributed backends in Scala. You lose type safety, FP patterns*, and the ability to reuse domain logic and shared libraries that drive the system’s behaviour.
In this article, we explore a different path: writing k6 tests in Scala via Scala.js. Same runtime model, same k6 ecosystem. We get compile-time guarantees, functional composition, and direct integration into Scala-based projects. Treat performance testing as a first-class software concern, not something done as a last piece of a puzzle, often by a separate team. We can tighten feedback loops, which can be a complement to the ubiquitous "shift-right" approach promoted by DevOps and SRE.
k6 has become one of the most popular tools for creating performance tests. Developers and QA engineers value it for its simplicity, readability, and ease of integration.
Grafana k6 is an open-source, developer-friendly, and extensible load testing tool. k6 allows you to prevent performance issues and proactively improve reliability.
k6 is a lightweight, compiled binary written in GO, embedding the Goja JavaScript interpreter. This design reflects a fundamental trade-off: leveraging the maturity and familiarity of the JavaScript ecosystem while maintaining the low resource consumption and efficiency of the Go language. As a result, test scripts are written in JavaScript. It is a practical choice since the language is well-known among both developers and QA engineers.
You can execute tests in your local environment or in a cloud environment with minimal boilerplate code. K6.io integrates well with Grafana, enabling near real-time monitoring of test execution. Its extension API allows you to use existing community extensions or develop your own. For example, to add support for custom network protocols.
While JavaScript is the first choice for many engineers, especially those working in software quality, it's not the only option worth considering. Scala, despite its reputation for complexity, offers strong interoperability and a powerful feature set that can be valuable in performance testing scenarios. Teams that already have their codebase written in Scala could benefit from it significantly.
In this article, we will highlight both the advantages and disadvantages that Scala brings to the table, helping you evaluate whether it might be a good fit for your use case. We will also outline how to integrate it with projects using a few Scalascala build tools: sbt, mill, and Gradle.
But first, we need to say a few words about Scala.js, which makes it possible.
Scala.js allows us to write applications in Scala that compile down to JavaScript and run in any modern browser or JavaScript runtime. This means you can leverage the static typing and advanced features of Scala - such as functional programming constructs, powerful collections, and expressive syntax - while still targeting the JavaScript ecosystem.
By doing so, Scala.js can help improve code quality and maintainability through stronger type safety and better compiler guarantees. Another advantage is the ability to reuse existing Scala libraries (limited to some degree) as well as integrate seamlessly with the extensive ecosystem of JavaScript libraries. This makes it a powerful bridge between the JVM world and the JavaScript runtime.
With this foundation in place, we can now show how to build a k6 library facade in Scala.js and begin prototyping our target solution.
The idea of using Scala.js with k6 started from a simple observation: while k6 offers an elegant way to write performance tests in JavaScript, it felt disconnected from projects that were already written in Scala. We wanted a way to reuse Scala’s type system and tooling, while still taking advantage of k6’s flexibility and ecosystem.
To verify if it is possible, we have done a simple scala-js project using Scala CLI:
It looks nice. Pretty neat implementation. In some cases, even sufficient if we want to have standalone tests, but the true benefits would be, as we stated earlier, if we could integrate it with existing projects. In the Scala world, there are three most significant build tools: sbt, mill, and Gradle. In all cases, we need k6 Grafana installed.
To check if it is feasible, we have created a simple project with appropriate tooling. For SBT, we have created a simple task:
Having a working solution and integrations with build tools in place, we wanted to measure the potential time overhead compared to "regular" JavaScript. To do this, we used the hyperfine tool, which offers a very simple syntax:
As we can see, even in a clean workspace, the compilation step introduces some overhead compared to the total test execution time. While this example is very simple, in real-world scenarios, the compilation time could be higher. On the other hand, incremental compilation will typically be used in most cases, which can significantly reduce this overhead.
When it comes to execution time, we do observe a difference. This may be attributed to the boilerplate code generated in the Scala.js version and its impact on k6's interpretation performance. Building tools based on executions gives even higher overhead. However, since execution time in typical load testing scenarios is measured in minutes, not seconds, this overhead should be negligible.
The performance results give us a clear picture of the runtime overhead. However, execution time is only one factor to consider when deciding whether Scala.js is a good fit for k6 tests. Let’s take a step back and look at the broader set of pros and cons.
Pros
Type-safety and IDE support
Integration with Scala (and possibly Java) based projects
There's no doubt - JavaScript is the first-choice language for k6. It's the native runtime, widely adopted, and extremely well-documented. For most teams, especially those just getting started with performance testing, JavaScript offers the fastest path to results with minimal setup.
But when does Scala.js make sense?
As mentioned earlier, Scala becomes a compelling option when you're already working within a Scala ecosystem - particularly in large, type-safe codebases where performance testing needs to be aligned closely with existing models or logic.
Beyond that, Scala.js can also be a great fit if you:
Value type safety to catch issues early and improve test reliability
Prefer a functional programming approach to test composition and logic
Want to reuse domain logic or data models directly in your performance tests
That said, it’s important to acknowledge the current limitations: This approach is still in its early stages. While promising, it requires further development to become fully production-ready - including full API coverage, proper packaging and publishing, tooling improvements, and seamless runtime integration.