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

multi-release jar for jdk11+ missing #237

Open
lanthale opened this issue Nov 30, 2019 · 15 comments
Open

multi-release jar for jdk11+ missing #237

lanthale opened this issue Nov 30, 2019 · 15 comments

Comments

@lanthale
Copy link

I am using the lib for a javafx application which I have ported from javafx8 to javafx11 and openjdk 11.

In order to use the lib I had to modularize the lib myself and therefore the question if it is possible to get a multi-release jar which can be used in java8 and java 9+ ?

Here is my config to use the lib (I have used moditec to modularize the lib):

<dependency>
            <groupId>com.github.bbottema</groupId>
            <artifactId>emailaddress-rfc2822</artifactId>
            <version>2.1.3</version>
            <exclusions>
                <exclusion>
                    <groupId>*</groupId>
                    <artifactId>*</artifactId>
                </exclusion>
            </exclusions>
        </dependency>
        <dependency>
            <groupId>com.sun.activation</groupId>
            <artifactId>jakarta.activation</artifactId>
            <version>1.2.1</version>
        </dependency>
        <dependency>
            <groupId>com.sun.mail</groupId>
            <artifactId>jakarta.mail</artifactId>
            <version>1.6.4</version>
            <exclusions>
                <exclusion>
                    <groupId>*</groupId>
                    <artifactId>*</artifactId>
                </exclusion>
            </exclusions>
        </dependency>
        <dependency>
            <groupId>org.simplejavamail</groupId>
            <artifactId>simple-java-mail</artifactId>
            <version>5.5.1</version>
            <exclusions>
                <exclusion>
                    <groupId>*</groupId>
                    <artifactId>*</artifactId>
                </exclusion>
            </exclusions>
</dependency>

Moditec config file or input for module-info.java

<module>
                                    <artifact>
                                        <groupId>org.simplejavamail</groupId>
                                        <artifactId>simple-java-mail</artifactId>                                   
                                    </artifact>                                    
                                    <moduleInfoSource>
                                        open module simple.java.mail {                                                                                                                                                                                                                                                                                                                                                                
                                        
                                        requires java.desktop;
                                        requires jakarta.mail;
                                        requires jakarta.activation;
                                        requires emailaddress.rfc2822; 
                                        requires org.slf4j;                                       
                                        
                                        exports org.simplejavamail;
                                        exports org.simplejavamail.converter;
                                        exports org.simplejavamail.email;
                                        exports org.simplejavamail.internal.util;
                                        exports org.simplejavamail.mailer;
                                        exports org.simplejavamail.outlookmessageparser.simplejavamail;
                                        exports org.simplejavamail.outlookmessageparser.simplejavamail.model;
                                        exports org.simplejavamail.outlookmessageparser.simplejavamail.rtf;
                                        exports org.simplejavamail.outlookmessageparser.simplejavamail.rtf.util;
                                        exports org.simplejavamail.springsupport;
                                        exports org.simplejavamail.util;
                                        }
                                    </moduleInfoSource>
                                </module> 
@bbottema
Copy link
Owner

Uhm, modularity is a little beyond my knowledge currently, but I have done some module-related work on the upcoming 6.0.0 release in the develop branch. I'm close to releasing it, would you mind trying a snapshot of that to see if it meets your requirements?

Otherwise, I'm happy to work with you to make it Java9+ compatible.

@lanthale
Copy link
Author

lanthale commented Dec 2, 2019

I will try that out. It is not so complicated at all you have just create a module-info.java(content is in my first post) in the root of the source folder and compile it with Option -release 8 and afterwards again with -release 11 for java9+. So you have inside the source folder another source folder for java 9+ which includes just the module-info.java. The rest of the code remains as it is.

But if you want to switch to java 9+ for the whole lib than create the module-info.java in the root folder and compile with java 9+ normally and you have the lib ready.

You can have a look here for more details:
https://www.baeldung.com/java-multi-release-jar

https://maven.apache.org/plugins/maven-compiler-plugin/multirelease.html

@bbottema
Copy link
Owner

bbottema commented Dec 2, 2019

Ok, so multireleases is something mostly useful for the library maintainers: they can leverage JDK functions that are not available in earlier JDKs and then release multiple versions of a class file in a single jar.

My question now is, why do you need this?

In order to use the lib I had to modularize the lib myself

I was under the impression that the module system is backwards compatible, split packages notwithstanding.

Why would I need two releases? Personally I'm not interested in maintaining two code bases.

@lanthale
Copy link
Author

lanthale commented Dec 2, 2019

Yes and no. The format of the module-info.java is only understand by a compiler greater than java 9. If you create the module-info.java and compile it with java 8 you will get errors. This is the only reason for the multirelease jar files. The multi-release jar prevents you from creating two jar files (one for java8 and one for java9) with two code bases.

Which JDK are you using to build the lib ?

For the reason above multi-release jar is the solution.
In this case in the directory for java 9+ only consists of the module-info.java. Therefore the compiler can create class files for java8 without the module-info.class and for the java9+ with the module-info.class. All other classes stay the same.

@lanthale
Copy link
Author

lanthale commented Dec 2, 2019

In the evening I will try it out and let write you what in the pom.xml must be changed and which file to place in which directory to archive all this above.

@lanthale
Copy link
Author

lanthale commented Dec 2, 2019

I have tried to commit but I think it was not successfully.

Please can you use the following maven plugin (readme explains that in more details):
https://github.com/metlos/multi-release-jar-maven-plugin

But you have to compile with java 9 at least. If you use java 11 you have to use additionally libs such as java.xml (was removed in java 11).

src/main/java-mr/9/module-info.java with the following content:

open module simple.java.mail {                                                                                                                                                                                                                                                                                                                                                                
                   
    requires java.desktop;
    requires jakarta.mail;
    requires jakarta.activation;
    requires emailaddress.rfc2822; 
    requires org.slf4j;                                       
                                        
    exports org.simplejavamail;
    exports org.simplejavamail.converter;
    exports org.simplejavamail.email;
    exports org.simplejavamail.internal.util;
    exports org.simplejavamail.mailer;
    exports org.simplejavamail.outlookmessageparser.simplejavamail;
    exports org.simplejavamail.outlookmessageparser.simplejavamail.model;
    exports org.simplejavamail.outlookmessageparser.simplejavamail.rtf;
    exports org.simplejavamail.outlookmessageparser.simplejavamail.rtf.util;
    exports org.simplejavamail.springsupport;
    exports org.simplejavamail.util;
}

@bbottema
Copy link
Owner

bbottema commented Dec 3, 2019

I'm still not clear on the issue here. What problem are we solving?

Why are you unable to use the library as-is? Newer JDK's should be backwards compatible with legacy jars, with the exception of split packages and J2EE modules.

@lanthale
Copy link
Author

lanthale commented Dec 3, 2019

I have now commit a working version which is usable with java9+ and has a minimal module-info.java included. For that I had to add some dependend jars and change the packaging goal from jar to multi-release-jar. At last I had to add two properties <maven.compiler.source>1.8</maven.compiler.source>
<maven.compiler.target>1.8</maven.compiler.target>

I tried to commit but had no right to commit and therefor as attachment the files.
pom.xml.zip
module-info.java.zip
multirelease-folder

Have a look on it and see if that is ok for you.

@bbottema
Copy link
Owner

bbottema commented Dec 9, 2019

@lanthale, you are focusing on the solution, while I'm still trying to understand the problem (or rather I fail to see a problem to begin with). So if you could please help me understand the problem if there really is one, then maybe we can move on to a solution.

@lanthale
Copy link
Author

lanthale commented Dec 9, 2019

Sorry I was too fast.
The problem is that actually your lib is treated as an automatic module in java 9 or newer which means that it is not possible to use jlink to create a distributable java app on any platform.

For a java-ee app on an application server this is not a problem, but for a desktop app it is.

So the files I added before are just adding the necessary information so that the lib is a valid named module with a defined interface for java beyond 9 and that the lib is in parallel useable under java 7 / 8.

Hopefully that clarified the issue a bit.
Do you have any questions ?

@bbottema
Copy link
Owner

I tried to commit but had no right to commit and therefor as attachment the files.

You can commit on a fork of this repo and then file a Pull Request to merge your changes into this repo. I would greatly appreciate some help with this.

Also notice some work is going on here as well to fix the Automatic-Module-Name.

@bbottema
Copy link
Owner

bbottema commented Feb 5, 2020

I just merged a pull request that fixes the module names. I hope to work on the multirelease item now.

One question, the requires/exports lines in module-info.java, is that manual work? Because that sounds aweful. Or did you generate that somehow?

@triceo
Copy link
Contributor

triceo commented Feb 5, 2020

@bbottema You can generate it with jdeps that comes with the JDK. But after that, you will most likely have to maintain it manually.

@francogp
Copy link

I'm using 6.5, and cannot compile using java 15:

java: module org.simplejavamail reads package org.simplejavamail.internal.modules from both org.simplejavamail and org.simplejavamail.core

@alainbodiguel
Copy link

Hi, same problem here with release 7.0.0 and java 17

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

No branches or pull requests

5 participants