Bug 479483 - [1.9][model] Define what is Module in Eclipse
Summary: [1.9][model] Define what is Module in Eclipse
Status: RESOLVED FIXED
Alias: None
Product: JDT
Classification: Eclipse Project
Component: Core (show other bugs)
Version: 4.5   Edit
Hardware: PC Windows 7
: P3 normal (vote)
Target Milestone: BETA J9   Edit
Assignee: JDT-Core-Inbox CLA
QA Contact: Jay Arthanareeswaran CLA
URL:
Whiteboard:
Keywords:
Depends on:
Blocks: 501162 482582 486011
  Show dependency tree
 
Reported: 2015-10-10 04:23 EDT by Jay Arthanareeswaran CLA
Modified: 2020-07-20 04:12 EDT (History)
25 users (show)

See Also:


Attachments
Thoughts and notes on Jigsaw from JavaOne 2015 (83 bytes, text/plain)
2015-10-27 19:10 EDT, Gunnar Wagenknecht CLA
no flags Details

Note You need to log in before you can comment on or make changes to this bug.
Description Jay Arthanareeswaran CLA 2015-10-10 04:23:55 EDT
Brought forward from bug 473901, comment #6:

My initial thought is that module
  - is a package fragment root (source/binary)
  - can be added to a Java project as a source folder (1x1)
  - can be added to a Java project as a JAR (1x1)
  - (s) can be added through Jimage files (many x 1)
  - Plain old src folders and Jars to be unnamed modules?

Questions:
 - What is the scope of the module system?
 - If we allow multiple modules in a project, and if there are dependent modules in another project, how does a depending module in another project read this module?
  - How does other components, notably PDE, see the modules (if at all)?
Comment 1 Jay Arthanareeswaran CLA 2015-10-13 06:58:39 EDT
We may also want to spare a thought for what will likely be a module in the J2EE world and how WTP will consume what we offer for module support.
Comment 2 Paul Benedict CLA 2015-10-26 14:30:01 EDT
Regarding comment #1:
- Why would a developer add a module as a source folder? A module is a type of dependency. If you're thinking about project references, you (1) add the dependency or (2) add an existing project that is a module... but #2 still seems superfluous since Eclipse is project based not module based. 

- Is multiple modules in a project feasible? I haven't read anything on modules being nested or allowing multiple module-info.java in a project.
Comment 3 Gunnar Wagenknecht CLA 2015-10-27 19:03:58 EDT
Jay, I started a document that captures my notes from JavaOne and thoughts. It's available for public comment. Once finalized, I can upload a PDF or some other document to this bug if you like.

https://docs.google.com/a/wagenknecht.org/document/d/1YHx26OJFSn0qPvBKmq9_RfHn7SJ2PBRg39svC6AjZe4/edit?usp=sharing
Comment 4 Gunnar Wagenknecht CLA 2015-10-27 19:10:43 EDT
Created attachment 257571 [details]
Thoughts and notes on Jigsaw from JavaOne 2015
Comment 5 Timo Kinnunen CLA 2015-10-28 00:01:33 EDT
Extending Platform Resources so that jar-file or module contents can be mounted inside the workspace as special folders providing read and write access to individual files would provide a lot of flexibility for working with them. Then, having multiple folders combine into one logical folder such that the contents of one of the folders are available as read-only in the other folders seems like what layers are supposed to be.
Comment 6 Jay Arthanareeswaran CLA 2015-10-29 02:09:41 EDT
(In reply to Gunnar Wagenknecht from comment #3)
> Jay, I started a document that captures my notes from JavaOne and thoughts.
> It's available for public comment. Once finalized, I can upload a PDF or
> some other document to this bug if you like.
> 
> https://docs.google.com/a/wagenknecht.org/document/d/
> 1YHx26OJFSn0qPvBKmq9_RfHn7SJ2PBRg39svC6AjZe4/edit?usp=sharing

Thanks Gunnar, this looks nice.

One clarification I seek is this: You have written

"The “unnamed” model can ready every other module (imports everything)
No other module can ever ready something from the “unnamed” module"

But I see this in The State of the Module:

"An unnamed module reads every other module, and it exports all of its packages to every other module."

which seems to conflict with what you said. Can you please clarify?
Comment 7 Gunnar Wagenknecht CLA 2015-10-29 08:46:34 EDT
(In reply to Jay Arthanareeswaran from comment #6)
> One clarification I seek is this: You have written
> 
> "The “unnamed” model can ready every other module (imports everything)
> No other module can ever ready something from the “unnamed” module"
> 
> But I see this in The State of the Module:
> 
> "An unnamed module reads every other module, and it exports all of its
> packages to every other module."
> 
> which seems to conflict with what you said. Can you please clarify?

Hmm ... what I meant to say is that no other module can depend on the unnamed module. The unnamed module exports all of its packages. I can see that the exports are required for not breaking reflection. But in reality, no module should be able to depend on the unnamed module, i.e. you can't declare a require "unnamed" in the module info.
Comment 8 Jay Arthanareeswaran CLA 2015-11-23 22:29:06 EST
(In reply to Jay Arthanareeswaran from comment #0)
>   - can be added to a Java project as a source folder (1x1)

In the current setup, this would require separate output folders for each source folder that is a module.
Comment 9 Paul Benedict CLA 2015-11-24 11:44:26 EST
So the intention here to allow one project to have multiple module source folders which means producing multiple module jars? If so, I am a critic of that choice. Each module, to me, seems like a new project with its own Java compiler configuration, etc. I don't understand the use case this multiplicity (complexity, really) is trying to support.
Comment 10 Jay Arthanareeswaran CLA 2015-11-25 06:44:38 EST
(In reply to Paul Benedict from comment #9)
> So the intention here to allow one project to have multiple module source
> folders which means producing multiple module jars? If so, I am a critic of
> that choice. Each module, to me, seems like a new project with its own Java
> compiler configuration, etc. I don't understand the use case this
> multiplicity (complexity, really) is trying to support.

It's not something we want to specifically support for modules, but something that comes along with Java projects - multiple source folders per project. I.e., assuming we decide on source folders being the equivalent of modules. I personally haven't thought about coming up with new java element for modules yet, which could mean more effort. But we will think about it if we have enough reasons.
Comment 11 Markus Keller CLA 2015-11-25 10:11:17 EST
Bug 105372 discusses the "multiple classpaths per project" request. I just explained in bug 105372 comment 19 why that's a no-go.

We should allow a Java project to become a module, but I don't think it makes sense to have multiple modules in one Java project.
Comment 12 Jay Arthanareeswaran CLA 2015-11-26 22:37:02 EST
Talking about modules in Eclipse Java projects, we should also keep in mind how we want the transition from regular Java projects with possibly multiple source folders into a project with module(s).
Comment 13 Jay Arthanareeswaran CLA 2015-12-03 04:55:53 EST
(In reply to Markus Keller from comment #11)
> Bug 105372 discusses the "multiple classpaths per project" request. I just
> explained in bug 105372 comment 19 why that's a no-go.

Whether we support multiple modules in a project or not, this particular problem you stated remains.

Let's say a Java project becomes a module. As a project it has the JRE in its build path. But as a module, for example, it only "requires" java.base. Now what should be the scope of the search etc. you mentioned?

As we already discussed, a IPackageFragmentRoot can naturally transform into a module, which means multiple modules inside a project will come free.

My recommendation is to let everything else (except the compiler i.e.) to have access to all that are in the project.
Comment 14 Paul Benedict CLA 2015-12-03 16:56:07 EST
Each module is just a JAR at packaging time. If you were to have a theoretical Eclipse project with N source modules, you're going to get N jars. Jay, is that the kind of output you're wanting to support? And why is that more preferable than setting up N Java Projects?
Comment 15 Jay Arthanareeswaran CLA 2015-12-03 22:14:37 EST
(In reply to Paul Benedict from comment #14)
> Each module is just a JAR at packaging time. If you were to have a
> theoretical Eclipse project with N source modules, you're going to get N
> jars. Jay, is that the kind of output you're wanting to support? And why is
> that more preferable than setting up N Java Projects?

I am not saying I prefer one over another. I was just saying it's possible to have both. People can choose to keep just one module in a project. Some of the existing APIs, such as IJavaProject#getPackageFragmentRoots() already have provision for such a multi-module/multi-classpath setup.
Comment 16 Sasikanth Bharadwaj CLA 2015-12-03 23:38:56 EST
(In reply to comment #14)
> Each module is just a JAR at packaging time. If you were to have a theoretical
> Eclipse project with N source modules, you're going to get N jars. Jay, is that
> the kind of output you're wanting to support? And why is that more preferable
> than setting up N Java Projects?
I don't think it's a question of one versus another. It's not that supporting multiple modules per project would preclude the users from having one module per project if that is the way they want it. And there probably will be a way of packaging multiple modules into a single archive. I feel that there's no need to impose such a restriction on projects since such support, quoting from Jay's comment, "will come free"
Comment 17 Gunnar Wagenknecht CLA 2015-12-04 04:58:24 EST
I think another limit of the "one-module-per-project" approach is JUnit tests. Although this isn't baked fully yet, Oracle expects tools to create test modules under the cover and patch modules under test for running such tests. It's very common for people to have tests within the same project.

Jay, what is your thinking around layers?
Comment 18 Paul Benedict CLA 2015-12-08 13:29:51 EST
(In reply to Gunnar Wagenknecht from comment #17)
> It's very common for people to have tests within the same project.

Gunnar, that is true. Regarding how to solve that problem, I have in mind one possible solution. For example, modules can be created dynamically via the Java API. So the JUnit tooling could be enhanced to create an in-memory module for all classes in src/test/java and use patching (-Xpatch option) to replace those in src/main/java.

(In reply to Sasikanth Bharadwaj from comment #16)
> I don't think it's a question of one versus another. It's not that
> supporting multiple modules per project would preclude the users from having
> one module per project if that is the way they want it. And there probably
> will be a way of packaging multiple modules into a single archive. 

Sasikanth, are you possibly referring to the JMOD format? That does allow multiple modules -- including configuration files and native code -- all to be packaged together in a ZIP. However, I still remain unconvinced an IDE should still support projects to output multiple modules; I feel it confuses concerns. Although a JMOD can contain multiple modules, it is not itself a module.

As I see it, developing multiple modules seems to be already appropriately supported by multiple IDE projects. Bundling them, one the other hand, seems more like a "project aggregator" function that either (1) is appropriate for yet another project (like the root of a Maven multi-module project) or (2) an enhancement to the Eclipse Export function.
Comment 19 Lars Vogel CLA 2015-12-08 15:35:16 EST
See also Bug 105372, which request multiple classpaths per project since a long time. Dani indicated that this bug may help to solve that requirement. See http://dev.eclipse.org/mhonarc/lists/ide-dev/msg01039.html
Comment 20 Timo Kinnunen CLA 2015-12-09 02:48:04 EST
(In reply to comment #18)
> However, I still remain unconvinced an IDE should
> still support projects to output multiple modules; I feel it confuses concerns.
> Although a JMOD can contain multiple modules, it is not itself a module.

The Java Builder has been able to output to multiple destination directories from one project for a long time. The only reason the incremental builder isn't already generating multiple .jars from one project today and the same for modules tomorrow is that Platform-Resources doesn't have a filesystem implementation in EFS supporting the zipfs.jar library, which was introduced in Java SE 7.

The way OpenJDK module implementation story appears to be unfolding is that zipfs looks likely to become the reference implementation and API for working with module files, while retaining existing support for ZIP and JAR files. The preferred API access would be via java.nio.file.* classes, FileSystemProvider, FileSystems and Files in particular. Files API of course supports the normal file systems too. The Eclipse codebase is still mostly in the java.io.File era so upgrading all tooling that may now need to work with modules to Java 7 in one fell swoop while ensuring coherence with the workbench resource model would be a big undertaking. 

Fortuitously the EFS and the Files API match pretty closely. Instead of one huge upgrade all at once, introducing a bridge between EFS and Java FileSystem APIs at the workbench level so that the existing model can be used to access both  would allow a much more gradual upgrade path for all affected tooling. Not to mention providing a whole new level of flexibility in setting up your Eclipse projects and artifacts to best fit your particular requirements.
Comment 21 Jay Arthanareeswaran CLA 2016-01-18 21:56:15 EST
(In reply to Gunnar Wagenknecht from comment #17)
> Jay, what is your thinking around layers?

Honestly, I haven't yet thought much about it. My initial thought was it wouldn't have much of an impact on the IDE? I could be wrong, though.
Comment 22 Jay Arthanareeswaran CLA 2016-02-22 01:57:42 EST
Here's another thought/question:

The scenario is about two modules (m1, m2) residing in their own projects (p1, p2) and and m2 requires m1. In order to compile m2, we need m1 and that, in terms of eclipse project dependencies, means p2 has p1 in its build path. However, in another scenario, where m1 exports a package to m2 explicitly, the module system needs access to m2 when compiling m1 or at least when resolving the module m1. In the current set-up (what we have in BETA_JAVA9), this fails because the module system works within the context of compilation. And we can't, obviously declare p1 to have p2 in its build path because that could be a cyclic dependency.

The module system (at least within the IDE) needs to be able to work beyond the boundaries of project dependencies. 

In the same context, I can imagine people saying, the need to define project dependency (along with module dependency) is redundant. This is something we need to have a good look at as we go forward. My opinion is that we should explore ways with which modules can be discovered and resolved entirely independent of project (dependency).
Comment 23 Jay Arthanareeswaran CLA 2016-02-23 00:42:04 EST
(In reply to Jay Arthanareeswaran from comment #22)
> The module system (at least within the IDE) needs to be able to work beyond
> the boundaries of project dependencies. 
> 
> In the same context, I can imagine people saying, the need to define project
> dependency (along with module dependency) is redundant. This is something we
> need to have a good look at as we go forward. My opinion is that we should
> explore ways with which modules can be discovered and resolved entirely
> independent of project (dependency).

One point against that argument: It would make it difficult to have multiple modules with same name in the workspace.
Comment 24 Gunnar Wagenknecht CLA 2016-02-23 04:42:05 EST
(In reply to Jay Arthanareeswaran from comment #23)
> > In the same context, I can imagine people saying, the need to define project
> > dependency (along with module dependency) is redundant. This is something we
> > need to have a good look at as we go forward. My opinion is that we should
> > explore ways with which modules can be discovered and resolved entirely
> > independent of project (dependency).
> 
> One point against that argument: It would make it difficult to have multiple
> modules with same name in the workspace.

How so? It's just a name/label. The locations should be enough to differentiate and identify them.

Note, I'm not saying that two modules with the same name in the module path makes sense. I'm not sure how the JRE would handle that. I'm trying to understand why this would be a problem for Eclipse?
Comment 25 Jay Arthanareeswaran CLA 2016-02-23 08:21:56 EST
(In reply to Gunnar Wagenknecht from comment #24)
> How so? It's just a name/label. The locations should be enough to
> differentiate and identify them.
> 
> Note, I'm not saying that two modules with the same name in the module path
> makes sense. I'm not sure how the JRE would handle that. I'm trying to
> understand why this would be a problem for Eclipse?

It wouldn't be difficult in the command line compiler, because we have the guidance of -modulepath. However, in the IDE, the usual of declaring dependencies is through projects, libraries and other kind of containers.

Now thinking about it a bit more, it might be reasonable to disallow them in the IDE too, because it is inline with our current behavior of not allowing projects/bundles with same name.
Comment 26 Markus Keller CLA 2016-06-15 06:01:11 EDT
(In reply to Jay Arthanareeswaran from comment #13)
> Let's say a Java project becomes a module. As a project it has the JRE in
> its build path. But as a module, for example, it only "requires" java.base.
> Now what should be the scope of the search etc. you mentioned?

For a module, it doesn't make sense to have additional stuff on the build path. A module can only depend on other modules. Therefore, the JRE build path entry of a module project should only be used to define the module path, i.e. the location of the required modules. The module-info.java defines what's going to be on the build path.
 
> As we already discussed, a IPackageFragmentRoot can naturally transform into
> a module, which means multiple modules inside a project will come free.

No, we won't break all APIs that assume that a project only has a single build path and a single set of settings. See bug 105372.

(In reply to Jay Arthanareeswaran from comment #25)
> However, in the IDE, the usual of declaring
> dependencies is through projects, libraries and other kind of containers.

Note that e.g. the "exports ... to" clause in the module-info will also need to be resolved, and those targets are not dependencies of the module. We probably need a per-workspace repository of modules, similar to PDE's "Target Platform" for OSGi bundles.
Comment 27 Jay Arthanareeswaran CLA 2016-06-15 11:16:31 EDT
(In reply to Markus Keller -- away till June 25 from comment #26)
> For a module, it doesn't make sense to have additional stuff on the build
> path. A module can only depend on other modules.

Now, that depends on what a module really is? Is it going to be another kind of IJavaProject? Is it not going to have a classpath? I think it should, because it is perfectly legal to compile a module with regular JAR files, which can only come from a classpath. If the module/project is going to have a classpath and have the JRE in the classpath (along with other JARs) the contribution of the JRE to a regular Java project and module project is different and must all be clearly defined.
Comment 28 Paul Benedict CLA 2016-06-15 12:49:47 EDT
The oddity here is that the compiler environment and runtime environment may be drastically different. For example, you could use Eclipse to build a fully functional module with appropriate "export" clauses... but then drop it on the classpath at runtime and have everything exported.

We can't control how the artifact will be consumed, but, I think the compiler environment *must* match how javac finds artifacts. Currently javac will resolve modules and export all types found on the classpath. Since that is both a valid compiler and runtime scenario, Eclipse needs to support both classpath and module paths.
Comment 29 Paul Benedict CLA 2016-06-20 12:41:06 EDT
Related to my comment #28, if one Eclipse project depends on another either through Java Build Path > Projects or Libraries > Add JARs, the user needs to specify to add it as a classpath entry or a module entry. The choice is necessary to support representing the intended usage. As I stated previously, a modularized jar may be dropped in the classpath for the sake of backward compatibility to export all types. The choice affects is critical to correctly correct or execute so it's a distinction that Eclipse needs to provide.
Comment 30 Manoj N Palat CLA 2016-09-01 00:17:00 EDT
A use case for java model element for module (atleast for module-info.java)
- Search for references for a package should include the exported packages of module-info.java.
Comment 31 Jay Arthanareeswaran CLA 2016-09-09 05:47:58 EDT
(In reply to Paul Benedict from comment #29)
> Related to my comment #28, if one Eclipse project depends on another either
> through Java Build Path > Projects or Libraries > Add JARs, the user needs
> to specify to add it as a classpath entry or a module entry. The choice is
> necessary to support representing the intended usage. As I stated
> previously, a modularized jar may be dropped in the classpath for the sake
> of backward compatibility to export all types. The choice affects is
> critical to correctly correct or execute so it's a distinction that Eclipse
> needs to provide.

Noted. We discussed this and plan to add some kind of a special container for modules. Any JAR can be added to this or directly to the project's build path. In the latter case, the JAR will be considered a plain old JAR. See also:

https://wiki.eclipse.org/JDT_Core/Java9/Open_items#Module_Path_Container

and other items on that page.
Comment 32 Jay Arthanareeswaran CLA 2017-01-05 03:48:53 EST
I received some commments from Remi Forax in an email discussion. Posting here for wider audience along with my response:

> Eclipse should be able to manage several modules in one Project because, i believe that compared to OSGi bundles or Maven artifacts, Java modules will be smaller.
>
> There are several reasons for supporting several modules in one project:
> - if you want to use the new visibility rules, e.g. non exported packages or non open packages, you need to wrap them into modules, so you end up with a lot of small modules.
>   Having a dozen of eclipse projects open is not very fun.

I don't think this is an issue. Eclipse handles tens of reasonably big projects for our own development quite well.

> - the module descriptor (module-info) resolution has cycle, restricted export (export to) and the directive provides usually goes in the opposite direction of the dependencies defined by the directive requires, so you need to resolve several module descriptors at the same time. Having all the dependent modules in the same project make sense.
> - support of javac module-source-path option, currently everything that javac can do, can be done in one eclipse project. If eclipse only support to have one module by project, on ant file will have to be mapped to different projects.

Having all dependent modules in a single project is very restrictive too, IMO. I am not even sure how this will work in a complex project. Imagine multiple teams working on different yet dependent components, or you grabbing a module from someone else. In these scenarios, importing modules into your existing setup is lot easier if they go to their own projects than an existing ones.

The only reason I suggested (in the beginning) to allow multiple modules in a project was because we could. But looks like the effort to support multiple classpaths per project is significant.
Comment 33 Jay Arthanareeswaran CLA 2017-07-21 02:10:42 EDT
I think we are more are less done here. This bug has served its purpose. Marking as resolved.
Comment 34 Christian Stein CLA 2020-07-18 21:57:36 EDT
*** Bug 565237 has been marked as a duplicate of this bug. ***