Jigsaw spec clarifications

classic Classic list List threaded Threaded
12 messages Options
Reply | Threaded
Open this post in threaded view
|

Jigsaw spec clarifications

Jonathan Gibbons
1. The uniqueness rule for provides services (It is a compile-time error
if more than one |provides| clause in a view indicates the same module
name or service name) is somewhat unclear about which of the names must
be unique.

What about
     provides service S with S_A;
     provides service S with S_B;

What about
     provides service S1 with S;
     provides service S2 with S;

Both of these would seem to be reasonable use cases.

2. The same rule for modules, can you provide different versions of a
module?
     provides M @ 1.0;
     provides M @ 2.0;
The spec implies not, which seems surprising for an alias mechanism.

3. I presume, but the spec does not say, that in "provides service S
with S_A" S_A should be a subtype of S.


-- Jon
Reply | Threaded
Open this post in threaded view
|

Re: Jigsaw spec clarifications

Jesse Glick
On 01/19/2012 05:33 PM, Jonathan Gibbons wrote:
> I presume, but the spec does not say, that in "provides service S with S_A" S_A should be a subtype of S.

Let us not forget that S_A must also be public, concrete, with a public default constructor, not a nested nonstatic class, and neither S nor S_A may have type arguments.
Generally that

try {
   S _ = new S_A();
} catch (Exception x) {}

must be compilable (without raw/unchecked warnings) from a hypothetical class in the same module but in its own package.
Reply | Threaded
Open this post in threaded view
|

Re: Jigsaw spec clarifications

Alex Buckley
In reply to this post by Jonathan Gibbons
The module name in a 'provides' clause (no 'service') is the identifier
immediately following 'provides' ... the service name in a 'provides
service' clause is the identifier immediately following 'service'.

Those are the identifiers which must be unique within a view.

I hope Alan can confirm my understanding of services as follows:

On 1/19/2012 2:33 PM, Jonathan Gibbons wrote:
> provides service S with S_A;
> provides service S with S_B;

Illegal. Ambiguity in which implementation to use.

> provides service S1 with S;
> provides service S2 with S;

Legal.

> 2. The same rule for modules, can you provide different versions of a
> module?
> provides M @ 1.0;
> provides M @ 2.0;
> The spec implies not, which seems surprising for an alias mechanism.

Illegal. If it was legal, do we want to infer that this module does
_not_ provide M @ 1.5? That seems over-complex to me - providing 2.0,
which indisputably happens above, usually means matching a requires
constraint of >= 1.5.

> 3. I presume, but the spec does not say, that in "provides service S
> with S_A" S_A should be a subtype of S.

Ah, I presume this too.

Alex
Reply | Threaded
Open this post in threaded view
|

Re: Jigsaw spec clarifications

Alex Buckley
On 1/19/2012 4:30 PM, Alex Buckley wrote:
> On 1/19/2012 2:33 PM, Jonathan Gibbons wrote:
>> provides service S with S_A;
>> provides service S with S_B;
>
> Illegal. Ambiguity in which implementation to use.

Actually, scratch that. Legal! It's clear from
http://openjdk.java.net/projects/jigsaw/doc/topics/services.html that a
module can offer multiple implementations of a service interface.

Alex
Reply | Threaded
Open this post in threaded view
|

Re: Jigsaw spec clarifications

Alan Bateman
In reply to this post by Alex Buckley
On 20/01/2012 00:30, Alex Buckley wrote:
> :
>
> I hope Alan can confirm my understanding of services as follows:
>
> On 1/19/2012 2:33 PM, Jonathan Gibbons wrote:
>> provides service S with S_A;
>> provides service S with S_B;
>
> Illegal. Ambiguity in which implementation to use.
I read your subsequent clarification and I agree it has to be legal (and
we have a test for this in the current services patch [1]).


>
>> provides service S1 with S;
>> provides service S2 with S;
>
> Legal.
Yes, but probably won't be too common (either S is an interface, or S1
or S2 is a subtype of the other).

As to one of Jesse's points, I don't think the current spec mandates
that the the service implementation have a public no-arg constructor.
javac doesn't check for this currently so it's possible to get a
ServiceConfigurationError at runtime for this case with the current
patch. An entry point on the other is specified to have a public static
void main method.

-Alan.

[1] http://cr.openjdk.java.net/~alanb/jigsaw-services/webrev/
Reply | Threaded
Open this post in threaded view
|

Re: Jigsaw spec clarifications

Jesse Glick
On 01/20/2012 07:28 AM, Alan Bateman wrote:
>>> provides service S1 with S;
>>> provides service S2 with S;
>
> probably won't be too common (either S is an interface

Impossible; it must be a concrete class.

> or S1 or S2 is a subtype of the other)

To the contrary I see this pattern all the time in NetBeans (*), without any subtype relationship between the interfaces:

module api {
   exports api;
}
package api;
public interface FrobnitzReader {
   java.io.Reader parse(java.io.File frobnitz);
}
package api;
public interface FrobnitzWriter {
   void store(java.io.File frobnitz, java.io.Writer writer);
}
module impl {
   requires api;
   provides service api.FrobnitzReader with impl.FrobnitzHandler;
   provides service api.FrobnitzWriter with impl.FrobnitzHandler;
}
package impl;
public class FrobnitzHandler implements api.FrobnitzReader, api.FrobnitzWriter {
   public java.io.Reader parse(java.io.File frobnitz) {...}
   public void store(java.io.File frobnitz, java.io.Writer writer) {...}
}

Nothing weird there that I can see; the author of impl merely preferred to keep related code in one source file.

(This does lead to a subtle point: currently ServiceProvider.load will always instantiate a fresh copy of each service implementation class every time you call it. This
means that nonstatic fields in a S.I. class, or an explicit constructor, are usually signs of a logic error. In the above example, it means that client code would get a
different FrobnitzHandler instance for reading vs. for writing. I do not think there is any reason to change this policy when SL is used in a modular environment, but it
should at least be documented whether SL may/must/must not cache instances. This is especially true since a system using dependency injection for the same purpose would
likely behave differently.)

> I don't think the current spec mandates that the the service implementation have a public no-arg constructor. javac doesn't check for this
> currently so it's possible to get a ServiceConfigurationError at runtime for this case

Seems like a defect in the spec. If there is some problem with the signature of the service that can reliably be detected at compile time, it should be treated as an error.


(*) Using the comparable @ServiceProvider, normally paired with Lookup.getDefault but also largely compatible with ServiceLoader.
Reply | Threaded
Open this post in threaded view
|

More reliable services was: Jigsaw spec clarifications

Jaroslav Tulach
>## 20. 1. 2012 15:54:56 ##<
> > I don't think the current spec mandates that the the service
> > implementation have a public no-arg constructor. javac doesn't check for
> > this currently so it's possible to get a ServiceConfigurationError at
> > runtime for this case
>
> Seems like a defect in the spec. If there is some problem with the
> signature of the service that can reliably be detected at compile time, it
> should be treated as an error.

+1

btw. when at rewriting the spec, could you consider including support for
static factory methods as proposed by
http://bugs.sun.com/view_bug.do?bug_id=6766540
?
-jt
Reply | Threaded
Open this post in threaded view
|

Re: Jigsaw spec clarifications

Alan Bateman
In reply to this post by Jesse Glick
On 20/01/2012 14:54, Jesse Glick wrote:
> On 01/20/2012 07:28 AM, Alan Bateman wrote:
>>>> provides service S1 with S;
>>>> provides service S2 with S;
>>
>> probably won't be too common (either S is an interface
>
> Impossible; it must be a concrete class.
There was a typo in my mail, I meant that S1 may be an interface of course.


> :
>
> (This does lead to a subtle point: currently ServiceProvider.load will
> always instantiate a fresh copy of each service implementation class
> every time you call it. This means that nonstatic fields in a S.I.
> class, or an explicit constructor, are usually signs of a logic error.
> In the above example, it means that client code would get a different
> FrobnitzHandler instance for reading vs. for writing. I do not think
> there is any reason to change this policy when SL is used in a modular
> environment, but it should at least be documented whether SL
> may/must/must not cache instances. This is especially true since a
> system using dependency injection for the same purpose would likely
> behave differently.)
This is something that comes up from time to time and I think we'll need
to support singleton services at some point.

>
>> I don't think the current spec mandates that the the service
>> implementation have a public no-arg constructor. javac doesn't check
>> for this
>> currently so it's possible to get a ServiceConfigurationError at
>> runtime for this case
>
> Seems like a defect in the spec. If there is some problem with the
> signature of the service that can reliably be detected at compile
> time, it should be treated as an error.
Yes, I think so too.

-Alan.
Reply | Threaded
Open this post in threaded view
|

Re: Jigsaw spec clarifications

Alex Buckley
On 1/20/2012 7:26 AM, Alan Bateman wrote:
>> Seems like a defect in the spec. If there is some problem with the
>> signature of the service that can reliably be detected at compile
>> time, it should be treated as an error.
> Yes, I think so too.

I added compile-time requirements for a service implementation to be
non-abstract, public, non-inner, and with a public no-args constructor.
The module declarations doc on the Jigsaw project page should refresh soon.

Alex
Reply | Threaded
Open this post in threaded view
|

Re: Jigsaw spec clarifications

Alan Bateman
On 20/01/2012 22:16, Alex Buckley wrote:
>
> I added compile-time requirements for a service implementation to be
> non-abstract, public, non-inner, and with a public no-args
> constructor. The module declarations doc on the Jigsaw project page
> should refresh soon.
I see the updates - thanks.

-Alan.
Reply | Threaded
Open this post in threaded view
|

Re: Jigsaw spec clarifications

Jonathan Gibbons
In reply to this post by Alex Buckley
On 01/19/2012 04:41 PM, Alex Buckley wrote:

> On 1/19/2012 4:30 PM, Alex Buckley wrote:
>> On 1/19/2012 2:33 PM, Jonathan Gibbons wrote:
>>> provides service S with S_A;
>>> provides service S with S_B;
>>
>> Illegal. Ambiguity in which implementation to use.
>
> Actually, scratch that. Legal! It's clear from
> http://openjdk.java.net/projects/jigsaw/doc/topics/services.html that
> a module can offer multiple implementations of a service interface.
>
> Alex


What about:
     provides service S with S_A;
     provides service S with S_A;

-- Jon

Reply | Threaded
Open this post in threaded view
|

Re: Jigsaw spec clarifications

Alex Buckley
On 1/24/2012 10:21 AM, Jonathan Gibbons wrote:
> What about:
> provides service S with S_A;
> provides service S with S_A;

We ban all other duplicates in a module declaration, even "harmless"
ones like "permits A; permits A;", so this should be illegal too. I will
update the compile-time and run-time rules.

Alex