Fix #5022: Eclipse jansi NPE; bump Maven wrapper to 3.9.9#5031
Merged
Conversation
The Eclipse "Debug Simulator" launch (and every other Maven-type launch
shipped by the archetype) used m2e's M2_RUNTIME=EMBEDDED, which on older
m2e bundles pulls in jansi 1.17.x. On JDK 16+ that jansi NPEs from
AnsiConsole.<clinit> -> getBoolean("jansi.passthrough") because the
property is unset and the buggy implementation dereferences the null
result. The JVM dies before Maven runs.
- Inject jansi.passthrough / jansi.strip / jansi.force = false into the
M2_PROPERTIES of every Maven-type .launch template so AnsiConsole's
init reads non-null values regardless of the embedded jansi version.
Same patch applied to the eclipse.zip the initializr serves.
- Bump the Maven Wrapper to Apache 3.3.2 / Maven 3.9.9 (only-script,
no jar) in the cn1app-archetype, the initializr's common.zip, and
the cn1playground and hellocodenameone dev projects. Modern jansi
(2.4.x) on the CLI side, no more Takari MavenWrapperDownloader.java,
and broader exercise of the new wrapper across the repo.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Collaborator
Author
|
Compared 20 screenshots: 20 matched. |
Contributor
✅ Continuous Quality ReportTest & Coverage
Static Analysis
Generated automatically by the PR CI workflow. |
Contributor
Cloudflare Preview
|
Collaborator
Author
|
Compared 106 screenshots: 106 matched. Benchmark Results
Build and Run Timing
Detailed Performance Metrics
|
Collaborator
Author
|
Compared 110 screenshots: 110 matched. Benchmark Results
Build and Run Timing
Detailed Performance Metrics
|
The old hellocodenameone/mvnw was a Takari wrapper hand-patched with an is_java17_home() probe that switched JAVA_HOME to a JDK 17 install when the inherited one wasn't 17. That hack was lost when this branch replaced mvnw with the canonical Apache wrapper, so the Android CI job fell back to the runner's JDK 8 and Maven's compiler died with "invalid target release: 17" against the project's <java.version>17. Mirror the pattern build-ios-app.sh already uses: wrap the mvnw call in a subshell that exports JAVA_HOME=JAVA17_HOME, and pass -Dmaven.compiler.fork=true / -Dmaven.compiler.executable as a belt-and-suspenders for any forked compile. Keeps the project's mvnw script identical to what new users get from the archetype. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Collaborator
Author
|
Compared 110 screenshots: 110 matched. Native Android coverage
✅ Native Android screenshot tests passed. Native Android coverage
Benchmark ResultsDetailed Performance Metrics
|
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
AnsiConsole.<clinit>NPE thrown by jansi 1.17.x on JDK 16+ when the Eclipse "Debug Simulator" (and friends) launches via m2e's embedded Maven. Injectjansi.passthrough=false,jansi.strip=false,jansi.force=falseintoM2_PROPERTIESof every Maven-type.launchtemplate so AnsiConsole reads non-null values regardless of which jansi the embedded Maven happens to bundle.only-scriptdistribution, no jar checked in). Applied to thecn1app-archetype, the initializr'scommon.zip, and toscripts/cn1playgroundandscripts/hellocodenameoneso the new wrapper gets exercised across the repo.Why the jansi properties matter
AnsiConsole.<clinit>callsgetBoolean("jansi.passthrough"); in jansi 1.17.x the implementation doesSystem.getProperty(name).equalsIgnoreCase("true")and NPEs when the property is unset. The Eclipse Console isn't a TTY, so the no-redirect branch that hides the bug doesn't fire. Setting any non-null value defuses it. This belt-and-suspenders fix works regardless of which jansi version the m2e EMBEDDED Maven happens to ship.Test plan
.launchtemplates have correct content; 15 Maven-type ones carry the three jansi entries, 2 group/remote ones are unchanged (no Maven invocation, no jansi concern).eclipse.ziprebuilt: 17 entries, 45 jansi lines, placeholders preserved (${project_loc:myappname},MyAppName - <action>.launch).common.ziprebuilt: surgically removed oldmvnw/mvnw.cmd/maven-wrapper.{jar,properties}/MavenWrapperDownloader.java; added Apache 3.3.2 wrapper files;mvnwretains executable bit.mvn clean installof the cn1app-archetype succeeds; generated project carries onlymaven-wrapper.propertiesin.mvn/wrapper/, executablemvnw, Eclipse launches with the jansi entries and correctly-substituted${project_loc:<artifactId>}../mvnw validateagainst bothscripts/cn1playgroundandscripts/hellocodenameonereturns BUILD SUCCESS on Maven 3.9.9 / JDK 25 with jansi 2.4.1 — no NPE, no plugin-resolution surprises from 3.6.3 -> 3.9.9.Notes / out of scope
tools/eclipse/__mainName__ - Remote Debug Simulator.launchhas a pre-existing hardcoded/eclipsetest1-commonliteral thatGeneratorModel's replacement list doesn't catch — separate bug, not fixed here.GeneratorModel.appendIdeSection's README blurb claimstools/eclipse/contains the launches in initializr-generated projects, but they actually land at the project root — also pre-existing, not in scope.🤖 Generated with Claude Code