I just remembered that option 2 wouldn’t be sufficient as it would only export 
at run time. The implementation needs access at compile time. I remember there 
are ways to achieve this but I don’t recall what they are at the moment, but I 
seem to recall is still requires calling module.exports.

Ralph

> On Oct 15, 2017, at 10:35 AM, Ralph Goers <ralph.go...@dslextreme.com> wrote:
> 
> Yes, you can target specific packages for exposure to specific modules. Yes, 
> we would want to move the classes that are “private” to a sub package of util 
> if we were to do that.
> 
> As for the name, yes you could specify multiple exports but that would mean 
> we would need to know the name of every log4j implementation that needs 
> access.  IMO, that would severely limit log4j-api’s usefulness as a logging 
> API. If we did that it would make more sense to say “All implementations must 
> use module name org.apache.logging.log4j.impl.” Of course, that limits us to 
> only allowing a single implementation at a time - which we don’t really 
> support now anyway (although we don’t preclude an enhancement to support it).
> 
> It is hard to say that there are any “best practices” for something that was 
> only officially released a month ago. At this point in time I think most 
> people are simply focusing on what the “proper” name should be for their 
> simple modules. It isn’t really all that common to what to have multiple 
> implementations of the same thing, but it isn’t all that unusual either. But 
> I can see several ways to wire these things:
> Use a single module name and specify it in module-info.java. This gives you 
> the benefit of also being able to export the private packages to the 
> implementation declaratively.
> Use the service loader (as we presently do). Use 
> provider.getClass().getModule() to locate the module the implementation is 
> in. Then call module.exports(packageName, targetModule) on the log4j-api 
> module to export the private packages to the implementation.
> 
> Personally, I like option 2 the best as it provides the most flexibility 
> while still achieving all the desired results and is pretty simple to 
> implement.
> 
> Ralph
> 
> 
>> On Oct 15, 2017, at 7:37 AM, Remko Popma <remko.po...@gmail.com> wrote:
>> 
>> You mean we may want to do something like this in the future?
>> 
>> module org.apache.logging.log4j {
>>   exports org.apache.logging.log4j;
>>   exports org.apache.logging.log4j.message;
>>   exports org.apache.logging.log4j.simple;
>>   exports org.apache.logging.log4j.spi;
>>   exports org.apache.logging.log4j.status;
>>   exports org.apache.logging.log4j.util to
>> org.apache.logging.log4j.impl; // only impl can see util
>>   uses org.apache.logging.log4j.spi.Provider;
>> }
>> 
>> The util package in log4j-api is actually a mixture of "consider private"
>> implementation classes and interfaces that are actually public API.
>> So some refactoring will be needed as you say.
>> 
>> Question: does it matter what the log4j-core module name is for the above?
>> Either impl or core would work, no?
>> If more modules need access, we can expand the list:
>> 
>> exports org.apache.logging.log4j.util to
>> org.apache.logging.log4j.core, some.external.impl, yet.another.impl;
>> 
>> 
>> I notice that the JDK module docs I've seen so far don't suggest the use of
>> an identical module name to prevent multiple implementations for a service
>> on the module path. The emphasis is more on detecting dependencies and
>> encapsulation, rather than preventing misconfiguration.
>> 
>> I wonder if there are other projects that use identical module names to
>> prevent misconfiguration. Is this a "best practice"?
>> 
>> Remko
>> 
>> 
>> On Sun, Oct 15, 2017 at 4:05 PM, Ralph Goers <ralph.go...@dslextreme.com>
>> wrote:
>> 
>>> FWIW, I am still torn on whether log4j-core should have a module name of
>>> org.apache.logging.log4j.core or org.apache.logging.log4j.impl. If it is
>>> the second then log4j-api could restrict exporting packages only meant for
>>> the implementation to that module. That would require some refactoring of
>>> the API classes but that shouldn’t be too big of a deal. Is the benefit of
>>> doing that greater than the (hypothetical) benefit of supporting multiple
>>> log4j implementations at the same time?  Should log4j-to-slf4j also then
>>> use the same module name since it replaces log4j-core?
>>> 
>>> Ralph
>>> 
>>>> On Oct 14, 2017, at 10:40 PM, Ralph Goers <ralph.go...@dslextreme.com>
>>> wrote:
>>>> 
>>>> I have committed the code for LOG4J2-2056. Log4j-api is a “real” module
>>> and has a module-info.java while all the rest that can be modularized are
>>> automatic modules.  Please review and test.
>>>> 
>>>> In order to create the module-info.java I had to do a few strange things:
>>>> Module-info.java is in the log4j-api-java9 project since log4j-api isn’t
>>> compiled with Java 9.
>>>> Compiling module-info.java requires that the packages being exported
>>> exist and have at least one class in them, so I had to create the
>>> directories and place a dummy java class in them.
>>>> The assembly that creates the log4j-api-java9 zip ignores all the dummy
>>> files and directories and only copies module-info.java and the two utility
>>> classes into the zip.
>>>> 
>>>> I have tested this with a simple program that only uses a module path
>>> but I would appreciate more extensive tests before it is released.
>>>> 
>>>> Ralph
>>> 
>>> 
>>> 
> 


Reply via email to