Module compilation unit grammar
Alex Buckley
alex.buckley at oracle.com
Fri Apr 1 16:22:33 PDT 2011
There are two ways to define export:
1) Export a package as a unit. No need for '.*' and it is impossible to
export individual types. (Allowing 'export p.q' to mean package p.q but
'export p.q.r' to mean type r in package p.q is too confusing, I think.)
2) Export individual types, and use '.*' to export all public types in
the package. Also '.**' to export all public types in subpackages.
I prefer (2) because:
- While it's appealing to think of a package as a unit, the reality is
that a package is nothing more than a qualifier on a type name. A module
system doesn't make a package visible per se; it makes certain public
types in a package visible.
- 'import' already provides a type-centric view of the world. Even if
you write 'import foo.*', you are aware of individual types within
package foo. I think we should stick with it for 'export'. Good practice
may end up being to export individual type names, as it is with import.
- It allows the .** "all subpackages" export, which (1) would enumerate
individually.
(2) adds the burden of classifying names as package names or type names;
see below. (2) also requires more of the module system, though in no way
does it cause split packages at runtime any more than (1).
I propose:
- 'export p' is invalid because p is not a qualified name.
- 'export p.q' means export the single type p.q.
- 'export p.*' means export all public types in package p.
- 'export p.**' means export all public types in package p and its
subpackages, and their subpackages, etc.
- 'export p.q.*' means export either all public types in package p.q or
all public member types in type q in package p - depending on p.q's
classification given the module's membership.
Alex
On 4/1/2011 3:33 PM, Mandy Chung wrote:
> Adding to Jon's question:
>
> export p.*;
>
> Does '*' match '.' in the package name? If not, it'd be useful to
> support '**' like syntax e.g. 'export java.**;' exports all package
> names with 'java.' prefix.
>
> Mandy
>
> On 4/1/11 3:05 PM, Jonathan Gibbons wrote:
>> Is the asterisk form of export constrained to packages and/or is it
>> required for packages?
>>
>> For example, which of the following are valid
>>
>> export p;
>> export p.*;
>> export p.Clazz;
>> export p.Clazz.*;
>>
>> -- Jon
>>
>>
>> On 03/11/2011 03:51 PM, Alex Buckley wrote:
>>> Here is the current grammar used by javac to parse a module
>>> compilation unit ("module-info.java").
>>>
>>>
>>> * Example
>>>
>>> module a.b @ 1.0 {
>>> require c.d @ [2.0,3.0);
>>> export e.f.*;
>>> provide g.h @ 4.0;
>>> permit i.j;
>>> class k.l;
>>> }
>>>
>>> - A compilation unit may contain a module declaration.
>>>
>>> - A module declaration may not be annotated.
>>>
>>> - A module name is a qualified identifier, in the spirit of a
>>> package-or-type name and a type name (JLS3 6.5).
>>>
>>> - A module version is like a qualified identifier, except that the
>>> characters of the identifier may be any Java letter or digit (to
>>> allow a first numeric character) and the qualifier may be .+-:~ (as
>>> per
>>> http://www.debian.org/doc/debian-policy/ch-controlfields.html#s-f-Version,
>>> referred to by org/openjdk/jigsaw/JigsawVersion.java).
>>>
>>> - require takes a qualified identifier indicating a module name,
>>> optionally followed by '@' and a version query. A version query is an
>>> exact version or an interval.
>>>
>>> - require supports 'local' and 'optional' flags. There is no 'public'
>>> flag because re-export is handled by the export statement.
>>>
>>> - export takes a qualified identifier indicating a package or type
>>> name, possibly ending in '. *'.
>>>
>>> - permit takes a qualified identifier indicating a module name.
>>>
>>> - class takes a qualified identifier indicating a type name.
>>>
>>> - require/local/optional/export/provide/permit are restricted keywords.
>>>
>>>
>>> * Grammar
>>>
>>> [x] denotes zero or one occurrences of x.
>>> {x} denotes zero or more occurrences of x.
>>> (x|y) means one of either x or y.
>>>
>>>
>>> CompilationUnit:
>>> [PackageDeclaration] [ImportDeclaration] [TypeDeclaration]
>>> [ModuleDeclaration]
>>>
>>> ModuleDeclaration:
>>> 'module' ModuleName ['@' Version] '{' {ModuleStatement} '}'
>>>
>>> ModuleName:
>>> Identifier
>>> ModuleName '.' Identifier
>>>
>>> ModuleStatement:
>>> ModuleRequire
>>> ModuleProvide
>>> ModuleExport
>>> ModulePermit
>>> ModuleClass
>>>
>>> ModuleRequire:
>>> 'require' [ModuleRequireModifier] ModuleName ['@' VersionQuery] ';'
>>>
>>> ModuleRequireModifier:
>>> 'local'
>>> 'optional'
>>>
>>> ModuleExport:
>>> 'export' PackageOrTypeName ['.' '*'] ';'
>>>
>>> ModuleProvide:
>>> 'provide' ModuleName ['@' Version] ';'
>>>
>>> ModulePermit:
>>> 'permit' ModuleName ';'
>>>
>>> ModuleClass:
>>> 'class' TypeName ';'
>>>
>>> VersionQuery:
>>> Version
>>> ('['|'(') Version ',' Version (')'|']')
>>>
>>> Version:
>>> ModuleIdentifier {VersionTokenizer ModuleIdentifier}
>>>
>>> ModuleIdentifier:
>>> JavaLetterOrDigit
>>> ModuleIdentifier JavaLetterOrDigit
>>>
>>> VersionTokenizer:
>>> . or + or - or : or ~
>>>
>>
>
More information about the jigsaw-dev
mailing list