Summary
During a migration from Solr 8.11 to Solr 9.10.1, a production deployment failed during the collection creation phase. The failure manifested as a RemoteSolrException stating: No ScriptEngine found by name: JavaScript. Despite explicitly enabling the scripting module via the JVM argument -Dsolr.modules=scripting, the ScriptUpdateProcessorFactory was unable to locate a valid execution engine to process the .js files defined in the solrconfig.xml.
Root Cause
The root cause is the removal of the Nashorn JavaScript engine from the standard Java runtime environment (JRE).
- JDK Evolution: Nashorn was deprecated in JDK 11 and completely removed in JDK 15.
- Solr 9 Architecture: Solr 9 moved toward a modular architecture. While the
scriptingmodule exists in Solr 9, it no longer bundles a built-in JavaScript engine by default because the underlying Java platform no longer provides one. - Engine Mismatch: The configuration explicitly requested
engine: JavaScript. Since the runtime environment (likely JDK 17+ in the Solr 9 Docker image) does not contain the Nashorn engine, theScriptEngineManagerreturns an empty list of supported engines, causing the core creation to fail.
Why This Happens in Real Systems
This is a classic example of transitive dependency breakage caused by platform upgrades.
- Platform Decoupling: In older versions, software engineers often relied on the “hidden” capabilities of the JVM (like Nashorn) rather than explicitly managing their engine dependencies.
- Breaking Changes in Upgrades: Major version bumps (Solr 8 to 9) often coincide with major JDK bumps (JDK 8 to JDK 17). When both happen simultaneously, the surface area for breaking changes increases exponentially.
- Implicit vs. Explicit Dependencies: The system was relying on an implicit dependency on the JDK’s internal scripting capabilities, which vanished during the infrastructure modernization.
Real-World Impact
- Deployment Blockage: Automated CI/CD pipelines fail during the “provisioning” stage, preventing new collections from being spun up.
- Migration Paralysis: Teams attempting to modernize their search stack find themselves unable to move forward without significant rewriting of configuration logic.
- Operational Downtime: If an emergency scale-out or shard rebalancing requires creating new collections via ConfigSets, the outage persists because the new cores cannot initialize.
Example or Code (if necessary and relevant)
The failing configuration in solrconfig.xml looks like this:
script1234.js
JavaScript
example config parameter
How Senior Engineers Fix It
A senior engineer looks beyond the immediate error and addresses the dependency lifecycle. There are three primary ways to fix this:
- Add the Engine Back (Short-term Fix): Explicitly include the Nashorn engine in the Solr classpath. This involves downloading the
nashorn-coreJAR and adding it to the Solrlibdirectory or using a custom Dockerfile to include it. - Migration to Groovy (Recommended): Replace JavaScript with Groovy. Groovy is more robust, performant for Solr update processors, and its dependency is explicitly managed. This requires rewriting the
.jsfiles into.groovyand updating theenginetag. - Logic Refactoring (Long-term Fix): Evaluate if the script is actually necessary. Most “scripted” updates can be replaced by Solr’s native Update Request Processors (like
AtomicUpdateorConditionalUpdate) which are faster, more stable, and require zero external scripting engines.
Why Juniors Miss It
- Focusing on the Symptom: Juniors often spend hours debugging the
solrconfig.xmlsyntax or checking if the-Dsolr.modules=scriptingflag was typed correctly, rather than investigating the underlying Java runtime capabilities. - Ignoring the Version Diff: They tend to assume that “Version 9” is just “Version 8 with more features,” failing to realize that the foundational ecosystem (the JDK) has changed fundamentally.
- Lack of Environment Awareness: They often test in local environments where a specific JDK might still have legacy features, failing to account for the strict, stripped-down environments found in production Docker containers.