Skip to content

fix(tomcat): restore context_path support from Ruby buildpack#1333

Open
stokpop wants to merge 5 commits into
cloudfoundry:mainfrom
stokpop:fix/tomcat-context-path
Open

fix(tomcat): restore context_path support from Ruby buildpack#1333
stokpop wants to merge 5 commits into
cloudfoundry:mainfrom
stokpop:fix/tomcat-context-path

Conversation

@stokpop

@stokpop stokpop commented Jun 25, 2026

Copy link
Copy Markdown
Contributor

Summary

  • JBP_CONFIG_TOMCAT context_path was implemented in the Ruby buildpack (2015)
    but never ported to the Go rewrite. Users setting context_path always got
    ROOT.xml and their app deployed at / regardless of config.
  • Adds ContextPath field to the Tomcat config struct, a contextXMLFilename()
    helper that implements the Tomcat convention (/foo/barfoo#bar.xml), and
    wires it into Finalize().
  • Empty or / context path → ROOT.xml (unchanged default).

Fixes #1331.

Tests

Unit tests added in tomcat_test.go (Finalize suite):

  • context_path: /the/intended/path → creates the#intended#path.xml, ROOT.xml absent
  • Empty context_pathROOT.xml (existing behaviour preserved)
  • context_path: /ROOT.xml
  • All pre-existing Finalize tests pass unchanged

context_path was implemented in the Ruby buildpack (commit 0186270,
2015) but never ported to Go. Users setting JBP_CONFIG_TOMCAT
context_path always got ROOT.xml regardless of config.

Tomcat convention: /foo/bar → foo#bar.xml (strip leading /, replace /
with #). Empty or / → ROOT.xml (root context, existing default).

Changes:
- Add ContextPath field to Tomcat config struct (yaml:"context_path")
- Add contextXMLFilename() helper implementing the path→filename transform
- Finalize() loads config if not already loaded (Supply() may not have
  run in all call paths), computes XML filename from context_path
- Three new tests (TDD): context_path set, empty, and /

Fixes cloudfoundry#1331.

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Restores support for configuring Tomcat’s deployment context via JBP_CONFIG_TOMCAT.tomcat.context_path, matching the legacy Ruby buildpack behavior (and fixing #1331) by creating the appropriate context XML filename instead of always writing ROOT.xml.

Changes:

  • Add ContextPath to the Tomcat config struct and derive the context XML filename from it.
  • Update Finalize() to write the context XML to the computed filename.
  • Add unit tests covering configured, empty, and / context paths.

Reviewed changes

Copilot reviewed 2 out of 2 changed files in this pull request and generated 2 comments.

File Description
src/java/containers/tomcat.go Adds context_path config support and uses it during Finalize() to select the context XML filename.
src/java/containers/tomcat_test.go Adds Finalize() tests validating filename selection for configured/empty/root context paths.
Comments suppressed due to low confidence (1)

src/java/containers/tomcat.go:617

  • The write error message still says failed to write ROOT.xml, but the target file may be something else when context_path is configured. This will make failures harder to diagnose.
		if err := os.WriteFile(contextXMLPath, []byte(contextContent), 0644); err != nil {
			return fmt.Errorf("failed to write ROOT.xml: %w", err)
		}

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment thread src/java/containers/tomcat.go
Comment thread src/java/containers/tomcat.go Outdated

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Copilot reviewed 2 out of 2 changed files in this pull request and generated 3 comments.

Comment thread src/java/containers/tomcat_test.go
Comment thread src/java/containers/tomcat_test.go
Comment thread src/java/containers/tomcat_test.go

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Copilot reviewed 2 out of 2 changed files in this pull request and generated 2 comments.

Comment thread src/java/containers/tomcat.go
Comment thread src/java/containers/tomcat_test.go
…igured; add explicit empty context_path test
@stokpop

stokpop commented Jun 25, 2026

Copy link
Copy Markdown
Contributor Author

Note: context_path deployment mechanism differs between Ruby and Go buildpack

Ruby buildpack (4.x) deploys the app into tomcat/webapps/<name>/ (e.g. webapps/foo#bar/) — Tomcat autodeploys from the webapps directory. No context descriptor XML is involved.

Go buildpack (5.x) uses Tomcat context descriptor files (conf/Catalina/localhost/<name>.xml) with docBase pointing at ${user.home}/app. This means the app is never placed in the webapps/ directory at all — even for the default root context (ROOT.xml points docBase at the app dir).

User-visible URL routing is identical: the application is accessible only at the configured path.

Potential behavioral difference: ServletContext.getRealPath() and any webapps-relative path assumptions will behave differently. In Ruby 4.x, getRealPath("/") resolves under tomcat/webapps/ROOT/ (or webapps/foo#bar/). In Go 5.x, it resolves under ${user.home}/app. This is a structural difference introduced by the Ruby→Go migration, not specific to this context_path PR — but this PR makes it visible for the non-root context case.

Question for reviewers: Is this getRealPath() behavioral difference expected/acceptable, or should the Go buildpack also place (or symlink) the app under tomcat/webapps/<name>/ to maintain full parity?

Details added to RUBY_VS_GO_BUILDPACK_COMPARISON.md §2A.11.

@ramonskie

Copy link
Copy Markdown
Contributor

Finding: context_path fix only covers exploded WARs.

Current Detect() accepts both:

  • exploded WAR: WEB-INF/
  • packaged WAR: *.war

But Finalize() only writes context descriptor when WEB-INF/ exists. So app.war + JBP_CONFIG_TOMCAT='{tomcat:{context_path:/foo}}' still no-op: no foo.xml, no ROOT.xml rewrite/removal.

Also integration test named “WAR file” does not deploy real .war; it deploys exploded tomcat_jakarta fixture (WEB-INF/...). Repo has no .war fixture.

ROOT.xml history matters here: current buildpack writes ROOT.xml after external config, so external config cannot reliably override root context. This PR helps that for exploded apps, but we need coverage proving:

  1. /foo serves OK
  2. / does not serve app
  3. packaged .war behavior fixed or explicitly unsupported
  4. external config + pre-existing ROOT.xml does not double-deploy

Without that, PR fixes happy path only, not full ROOT.xml/context_path problem.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Tomcat JBP_CONFIG_TOMCAT context_path not applied in v5

3 participants