Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add support for builds where the build result is a JAR, not exploded JAR #223

Closed
dmikusa opened this issue Jun 14, 2022 · 4 comments
Closed
Labels
type:enhancement A general enhancement

Comments

@dmikusa
Copy link
Contributor

dmikusa commented Jun 14, 2022

What happened?

Maven/Gradle buildpacks can produce a single JAR, in which case that JAR is exploded into the /workspace directory. Spring Boot CNB expects this case.

The Maven/Gradle buildpacks can also produce multiple output files. The executable-jar CNB has support for this. It will filter and find the first JAR that is executable & use java -jar as the command to run the app. This isn't presently going to work with the Spring Boot buildpack, because we expect there to be an exploded JAR for some of the features (like slices).

Support for multiple build artifacts is a relatively new feature. 1.) Explore how that fully impacts Spring Boot CNB and 2.) Make whatever accommodations are necessary to make things work as expected (or possibly emit a warning that features are not supported in this mode).

@dmikusa dmikusa added the type:enhancement A general enhancement label Jun 14, 2022
@anthonydahanne
Copy link
Member

anthonydahanne commented Feb 17, 2024

I've somehow worked around this problem with this commit:
paketo-buildpacks/executable-jar@8eef8f3

it's basically saying: if there's an executable jar, then I should explode it no matter what, and discard everything else (which works great with gradle boot plugin that by default produces 2 jars: spring boot and plain)

I've tried fixing this from the Spring Boot buildpack BUT... my hands were tied because executable-jar already had set the launch process to be java -jar sb.jar and my fix was to explode it and remove the original jar.

I guess I could revisit this SB buildpack attempt if only I could rewrite the launch process.
Issue then would be executable-jar telling a lie with java -jar when sb buildpack further down the line would rewrite to java MyMain (AFAIR, there's another case that makes executable-jar tell a lie with its process list, native possibly)

@dmikusa
Copy link
Contributor Author

dmikusa commented Feb 19, 2024

I don't think we could do that in general at the executable-jar level because some app types produce a JAR and expect to have a JAR (I believe Quarkus does this).

Taking a step back. You're right that this goes back to the introduction of multi-build output file support. When we introduced the ability to build multiple outputs, that caused Spring Boot Gradle apps to trigger the multi-build output behavior because Spring Boot Gradle projects are producing two JARs by default.

This isn't exactly a problem, but it will trigger the logic in libbs to do a multi-JAR build. There's no way that we can prevent that at the libbs level because it's not aware of the specifics of the application beyond the build tool that's running (i.e. it doesn't know that it's a Spring Boot app). Putting Spring Boot-specific logic into libbs is not something I'd prefer to do. We want to try and keep that in the Spring Boot buildpack. That means at the libbs-level, there's not anything that we can do because it's completely legitimate that an app might produce two JAR files and need both to run.

The present solution is not a great UX, but it is to simply push back and have users disable producing the second JAR file by changing their build.gradle file. I know it's annoying because for every new project I create I forget to make this change too. I certainly feel the pain.

It is possible that we can handle this in other buildpacks. Before talking about how we do that, I was trying to figure out if we should.

We know that Spring Boot Gradle projects will produce two JAR files by default, but this isn't a legitimate multi-JAR need. It's just coincidental.

Do we have use cases for Spring Boot apps where there is a legitimate need to support multi-JAR builds? I think #117 was potentially one, but I don't know if the thin launcher is still a thing or will ever make it out of experimental status. If we do have use cases, then we need to document those (how they'd be triggered/sample apps) and plan for this in the solution.

I think this is important because one potentially valid solution is to just never support a multi-build output for Spring Boot apps. We can continue to recommend users handle this by a small one-time build.gradle change and if we hit cases in the Spring Boot buildpack when there is a JAR where there should be expanded files, then we fail the build.

@anthonydahanne
Copy link
Member

I think it got solved by @pivotal-david-osullivan in #427

we'll close this issue once this above PR is merged

@anthonydahanne
Copy link
Member

@dmikusa let me know if you want to revisit this, after the CDS MR is merged

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
type:enhancement A general enhancement
Projects
None yet
Development

No branches or pull requests

2 participants