Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-03-06 Thread Chris Lattner via swift-evolution
On Mar 5, 2017, at 4:21 AM, Joanna Carter via swift-evolution 
 wrote:
> 
> I have to say, I really *hate* "Swift style". It wouldn't be so bad if I 
> could change the indentation rules in Xcode.
> 
> For over 25 years, I have written code with curly braces always on their own 
> line, opening ones aligned with the start of the preceding line.
> 
> As for switch..case statement indenting, the default supplied by code 
> completion is laid ou thus :
> 
>switch value {
>case pattern:
>  code
>default:
>  code
>}
> 
> Whereas, for Objective-C, code completion gives us :
> 
>switch (value) {
>  case pattern:
>code
>break;
> 
>  default:
>break;
>}

I can understand how you might find this unnerving, but it is important to 
understand that Swift and Objective-C/C have different semantics when it comes 
to case labels:  in Swift, a case label *is* a scope, and *is* part of the 
switch statement.  In Objective-C, a case label is just a label, like any other 
goto label: it is not a scope and is not necessarily a direct child of the 
switch statement.

C and Objective-C’s behavior is what leads to obscure but important things like 
Duff’s device (https://en.wikipedia.org/wiki/Duff's_device 
).  

In contrast, Swift fixes the scoping, fallthrough, and other related problems 
all in one fell swoop, and ensures that cases are directly nested under the 
switch (unlike in C, where they can be nested under other statements within the 
switch).  Because the case/default labels are *part of* the switch in Swift, it 
makes sense for them to be indented at the same level.

While I can respect that you aesthetically have a preference for the 
Objective-C way of doing things, the rationale for this behavior change wasn’t 
arbitrary and wasn’t due to "LLVM style".  It is an important reflection of the 
core semantics of the language model.

Finally, conservation of horizontal whitespace is important for comprehension 
of code, particularly w.r.t. readability and maintenance.  This is why 
statements like guard exist: to reduce nesting and indentation, directing the 
attention of someone reading and maintaining code to the important parts.

-Chris


___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-03-05 Thread Robert Widmann via swift-evolution
A lot of “Swift Style” is “LLVM Style” enforced in little corners of the 
language (I, too, like to keep my cases indented a bit further).  There are 
formatting tools available to make your Swift look C#-ish if you want :)

> On Mar 5, 2017, at 7:21 AM, Joanna Carter via swift-evolution 
>  wrote:
> 
>> It's part of what has become Swift style and I'm quite happy about it. 
>> Indent on case and on case content is too much indenting :)
>> 
>>> On 3 Mar 2017, at 11:06, Karl Wagner via swift-evolution 
>>>  wrote:
>>> 
>>> 
 On 3 Mar 2017, at 05:52, T.J. Usiyan via swift-evolution 
  wrote:
 
 I would rather that we use the (not-entirely-pleasant-to-me) "curly brace 
 without an indent" used for switches+cases.  
>>> 
>>> Is that actually “how we do things in Swift”? I always thought it was just 
>>> Xcode being silly…
>>> 
>>> I should probably file a radar about it in either case.
> 
> I have to say, I really *hate* "Swift style". It wouldn't be so bad if I 
> could change the indentation rules in Xcode.
> 
> For over 25 years, I have written code with curly braces always on their own 
> line, opening ones aligned with the start of the preceding line.
> 
> As for switch..case statement indenting, the default supplied by code 
> completion is laid ou thus :
> 
>switch value {
>case pattern:
>  code
>default:
>  code
>}
> 
> Whereas, for Objective-C, code completion gives us :
> 
>switch (value) {
>  case pattern:
>code
>break;
> 
>  default:
>break;
>}
> 
> With Objective-C, all I had to do was move the opening curly brace to the 
> next line and Xcode would keep the same indentation :
> 
>switch (value)
>{
>  case pattern:
>code
>break;
> 
>  default:
>break;
>}
> 
> Now, in Swift, not only do I not have the ability to group lines of code 
> together with braces (interpreted as a closure), if I move the opening brace 
> to the next line and indent the cases (for clarity) :
> 
>switch value
>{
>  case pattern:
>code
>  default:
>code
>}
> 
> … although the opening brace stays put, as soon as I reformat a block of code 
> that includes the switch, I automatically lose the indentation of my cases!
> 
> And, no matter what I do in Xcode preferences, I don't seem to be able to 
> achieve *my* coding standards for Swift.
> 
> There are days when I feel like reverting to Objective-C
> 
> --
> Joanna Carter
> Carter Consulting
> 
> ___
> swift-evolution mailing list
> swift-evolution@swift.org
> https://lists.swift.org/mailman/listinfo/swift-evolution

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-03-05 Thread Robert Widmann via swift-evolution


~Robert Widmann

2017/03/03 16:10、Matthew Johnson  のメッセージ:

> 
>> On Mar 2, 2017, at 10:52 PM, T.J. Usiyan  wrote:
>> 
>> Submodules will, I hope, afford us the ability to share meaningfully 
>> arranged API. In an ideal scenario, I could have a module that has all of 
>> the smaller pieces of 'utilities and conveniences' that one builds up  
>> broken into submodules. Importing one of the submodules from its enclosing 
>> module shouldn't bring anything extra along. I don't think that we need to 
>> add nearly as many new concepts as `scope-based submodules` introduces. "ABI 
>> Boundaries", "Name Boundaries", "Scope Boundaries”?
> 
> These boundaries already exist.  All the proposal does is give a name to them.

Some of these boundaries (at least the first) are not meant to be user-visible. 
 Some already exist and are just specializations of lexical scope for some 
reason.

> 
>> What he have is built on LLVM Modules and holds together fairly well on its 
>> own. 
>> Our projects, at present, are a module. ABI doesn't have very much to do 
>> with the 'boundary' of our target. The wording around Module maps make it 
>> clear that submodules have been considered Module Maps 
>> 
>> Export statements are not a useful addition. Access modifiers capture this 
>> well enough via open|public etc. When paired with robust import syntax, we 
>> would have everything that we need. 
> 
> Can you elaborate on what you mean by “robust import syntax”?  The top-level 
> export statement has similar semantics to the `public import` in Robert and 
> Jaden’s proposal.  They even used the word “export” in describing the 
> semantics of `public import`.
> 
> It just uses the name `export` rather than `import` to avoid overloading the 
> semantics of `import` and introduces additional features to avoid coupling 
> the internal structure of a module to the view exposed to users of the module.
> 

What about this constitutes an overload?  Importing a (sub)module and exporting 
a (sub)module may sound disjoint because in common parlance they are opposites. 
 As it relates to programming languages, an export is an iteration upon an 
import, a step up.  Where an import opens a submodule's contents to the 
importer, an export opens a submodule's contents to an importer once removed.  
As such, the term "re-export" is sometimes used to make this clear.  We 
represent such relationships with qualifiers, not new declarations.

>> 
>> The changes to scope and access modifiers in `scope-based submodules` are 
>> dramatic and don't seem to pay for themselves at all.
> 
> This aspect makes the proposal more powerful but is not essential to 
> scope-based submodules.  It has been broken out into an independent proposal 
> which so far has received very positive feedback.

>>  
>> 
>> "Top of the file" declaration to declare a submodule is not at all desirable 
>> to me. I would rather that we use the (not-entirely-pleasant-to-me) "curly 
>> brace without an indent" used for switches+cases.  
> 
> If it’s not entirely pleasant why do you prefer that style?
> 
>> 
>> LLVM modules handle circularity, I think. 
> 
> Do you believe circularity is important?  What use cases do you have for that?

What reasons do you have for disallowing it?  If two (sub)modules depend on 
each other's contents and cannot be cleanly nested into each other, their 
dependency is mutual.  We do not have a preprocessor - our modules are semantic 
rather than syntactic - so there isn't a risk of strange behavior like there is 
in older languages.

> 
>> 
>> The ability to import a single type or a list of specific types is of great 
>> value, in my opinion, especially when paired with renaming (we don't have it 
>> but one can dream, no?) Qualified imports are obviously the tact that I 
>> would like to make this possible. Allow the consumer of the API to get as 
>> specific as they need to when importing. I consider it an unfortunate 
>> concession that `import This.That.TheOther` imports as much as it does but 
>> it is, basically, the only major issue that I have with this proposal and it 
>> can't be helped without breaking compatibility. 
> 
> Selective import is an additive feature that is orthogonal to submodules.  I 
> agree that it would be very nice to have, but it is a separate issue IMO.

No it is not. I agree it is a separate issue, but you cannot acknowledge that 
the current behavior is strange and brush it off.

> 
>> 
>> Overall, it is my opinion that we should solve the submodule and import 
>> problems with changes like those proposed here. Modify very little of the 
>> current syntax and semantics. What we have is fairly close and can actually 
>> be coherent even with the additional burden of exposing submodules.
> 
> It sounds like you don’t view encapsulation as an important feature of 
> submodules.  Is that correct?  If so, why not?  Do you believe we need 
> encapsulation boundaries larger 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-03-05 Thread Joanna Carter via swift-evolution
> It's part of what has become Swift style and I'm quite happy about it. Indent 
> on case and on case content is too much indenting :)
> 
>> On 3 Mar 2017, at 11:06, Karl Wagner via swift-evolution 
>>  wrote:
>> 
>> 
>>> On 3 Mar 2017, at 05:52, T.J. Usiyan via swift-evolution 
>>>  wrote:
>>> 
>>> I would rather that we use the (not-entirely-pleasant-to-me) "curly brace 
>>> without an indent" used for switches+cases.  
>> 
>> Is that actually “how we do things in Swift”? I always thought it was just 
>> Xcode being silly…
>> 
>> I should probably file a radar about it in either case.

I have to say, I really *hate* "Swift style". It wouldn't be so bad if I could 
change the indentation rules in Xcode.

For over 25 years, I have written code with curly braces always on their own 
line, opening ones aligned with the start of the preceding line.

As for switch..case statement indenting, the default supplied by code 
completion is laid ou thus :

switch value {
case pattern:
  code
default:
  code
}

Whereas, for Objective-C, code completion gives us :

switch (value) {
  case pattern:
code
break;

  default:
break;
}

With Objective-C, all I had to do was move the opening curly brace to the next 
line and Xcode would keep the same indentation :

switch (value)
{
  case pattern:
code
break;

  default:
break;
}

Now, in Swift, not only do I not have the ability to group lines of code 
together with braces (interpreted as a closure), if I move the opening brace to 
the next line and indent the cases (for clarity) :

switch value
{
  case pattern:
code
  default:
code
}

… although the opening brace stays put, as soon as I reformat a block of code 
that includes the switch, I automatically lose the indentation of my cases!

And, no matter what I do in Xcode preferences, I don't seem to be able to 
achieve *my* coding standards for Swift.

There are days when I feel like reverting to Objective-C

--
Joanna Carter
Carter Consulting

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-03-03 Thread Matthew Johnson via swift-evolution

> On Mar 2, 2017, at 10:52 PM, T.J. Usiyan  wrote:
> 
> Submodules will, I hope, afford us the ability to share meaningfully arranged 
> API. In an ideal scenario, I could have a module that has all of the smaller 
> pieces of 'utilities and conveniences' that one builds up  broken into 
> submodules. Importing one of the submodules from its enclosing module 
> shouldn't bring anything extra along. I don't think that we need to add 
> nearly as many new concepts as `scope-based submodules` introduces. "ABI 
> Boundaries", "Name Boundaries", "Scope Boundaries”?

These boundaries already exist.  All the proposal does is give a name to them.

> What he have is built on LLVM Modules and holds together fairly well on its 
> own. 
> Our projects, at present, are a module. ABI doesn't have very much to do with 
> the 'boundary' of our target. The wording around Module maps make it clear 
> that submodules have been considered Module Maps 
>  
> 
> Export statements are not a useful addition. Access modifiers capture this 
> well enough via open|public etc. When paired with robust import syntax, we 
> would have everything that we need. 

Can you elaborate on what you mean by “robust import syntax”?  The top-level 
export statement has similar semantics to the `public import` in Robert and 
Jaden’s proposal.  They even used the word “export” in describing the semantics 
of `public import`.

It just uses the name `export` rather than `import` to avoid overloading the 
semantics of `import` and introduces additional features to avoid coupling the 
internal structure of a module to the view exposed to users of the module.

> 
> The changes to scope and access modifiers in `scope-based submodules` are 
> dramatic and don't seem to pay for themselves at all.

This aspect makes the proposal more powerful but is not essential to 
scope-based submodules.  It has been broken out into an independent proposal 
which so far has received very positive feedback.

>  
> 
> "Top of the file" declaration to declare a submodule is not at all desirable 
> to me. I would rather that we use the (not-entirely-pleasant-to-me) "curly 
> brace without an indent" used for switches+cases.  

If it’s not entirely pleasant why do you prefer that style?

> 
> LLVM modules handle circularity, I think. 

Do you believe circularity is important?  What use cases do you have for that?

> 
> The ability to import a single type or a list of specific types is of great 
> value, in my opinion, especially when paired with renaming (we don't have it 
> but one can dream, no?) Qualified imports are obviously the tact that I would 
> like to make this possible. Allow the consumer of the API to get as specific 
> as they need to when importing. I consider it an unfortunate concession that 
> `import This.That.TheOther` imports as much as it does but it is, basically, 
> the only major issue that I have with this proposal and it can't be helped 
> without breaking compatibility. 

Selective import is an additive feature that is orthogonal to submodules.  I 
agree that it would be very nice to have, but it is a separate issue IMO.

> 
> Overall, it is my opinion that we should solve the submodule and import 
> problems with changes like those proposed here. Modify very little of the 
> current syntax and semantics. What we have is fairly close and can actually 
> be coherent even with the additional burden of exposing submodules.

It sounds like you don’t view encapsulation as an important feature of 
submodules.  Is that correct?  If so, why not?  Do you believe we need 
encapsulation boundaries larger than a file but smaller than a module?

>  
> 
> 
> 
> On Thu, Mar 2, 2017 at 11:01 PM, Matthew Johnson  > wrote:
> 
> 
> Sent from my iPad
> 
> On Mar 2, 2017, at 9:06 PM, T.J. Usiyan  > wrote:
> 
>> +1 overall. prefer this approach over the "scope based" approach in the 
>> other proposal
> 
> Can you elaborate?  What problems are you hoping submodules will address?
> 
>> 
>> On Wed, Feb 22, 2017 at 10:10 AM, Matthew Johnson via swift-evolution 
>> > wrote:
>> 
>>> On Feb 21, 2017, at 11:54 PM, Robert Widmann >> > wrote:
>>> 
>>> 
 On Feb 22, 2017, at 12:41 AM, Matthew Johnson > wrote:
 
 
 
 Sent from my iPad
 
 On Feb 21, 2017, at 11:09 PM, Robert Widmann > wrote:
 
> 
>> On Feb 21, 2017, at 11:59 PM, Matthew Johnson > > wrote:
>> 
>> 
>>> On Feb 21, 2017, at 10:41 PM, Robert Widmann >> 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-03-02 Thread T.J. Usiyan via swift-evolution
Submodules will, I hope, afford us the ability to share meaningfully
arranged API. In an ideal scenario, I could have a module that has all of
the smaller pieces of 'utilities and conveniences' that one builds up
 broken into submodules. Importing one of the submodules from its enclosing
module shouldn't bring anything extra along. I don't think that we need to
add nearly as many new concepts as `scope-based submodules` introduces.
"ABI Boundaries", "Name Boundaries", "Scope Boundaries"? What he have is
built on LLVM Modules and holds together fairly well on its own.
Our projects, at present, are a module. ABI doesn't have very much to do
with the 'boundary' of our target. The wording around Module maps make it
clear that submodules have been considered Module Maps


Export statements are not a useful addition. Access modifiers capture this
well enough via open|public etc. When paired with robust import syntax, we
would have everything that we need.

The changes to scope and access modifiers in `scope-based submodules` are
dramatic and don't seem to pay for themselves at all.

"Top of the file" declaration to declare a submodule is not at all
desirable to me. I would rather that we use the
(not-entirely-pleasant-to-me) "curly brace without an indent" used for
switches+cases.

LLVM modules handle circularity, I think.

The ability to import a single type or a list of specific types is of great
value, in my opinion, especially when paired with renaming (we don't have
it but one can dream, no?) Qualified imports are obviously the tact that I
would like to make this possible. Allow the consumer of the API to get as
specific as they need to when importing. I consider it an unfortunate
concession that `import This.That.TheOther` imports as much as it does but
it is, basically, the only major issue that I have with this proposal and
it can't be helped without breaking compatibility.

Overall, it is my opinion that we should solve the submodule and import
problems with changes like those proposed here. Modify very little of the
current syntax and semantics. What we have is fairly close and can actually
be coherent even with the additional burden of exposing submodules.



On Thu, Mar 2, 2017 at 11:01 PM, Matthew Johnson 
wrote:

>
>
> Sent from my iPad
>
> On Mar 2, 2017, at 9:06 PM, T.J. Usiyan  wrote:
>
> +1 overall. prefer this approach over the "scope based" approach in the
> other proposal
>
>
> Can you elaborate?  What problems are you hoping submodules will address?
>
>
> On Wed, Feb 22, 2017 at 10:10 AM, Matthew Johnson via swift-evolution <
> swift-evolution@swift.org> wrote:
>
>>
>> On Feb 21, 2017, at 11:54 PM, Robert Widmann 
>> wrote:
>>
>>
>> On Feb 22, 2017, at 12:41 AM, Matthew Johnson 
>> wrote:
>>
>>
>>
>> Sent from my iPad
>>
>> On Feb 21, 2017, at 11:09 PM, Robert Widmann 
>> wrote:
>>
>>
>> On Feb 21, 2017, at 11:59 PM, Matthew Johnson 
>> wrote:
>>
>>
>> On Feb 21, 2017, at 10:41 PM, Robert Widmann 
>> wrote:
>>
>> By API boundaries I mean both the one internal to MyModule.Foo and the
>> one defined by MyModule.  Here “the API boundary” is explicitly about the
>> submodule MyModule.Foo, whose internal state may have been “unsealed” in
>> the top level by the extension, but has not been re-exported.
>>
>>
>> I’m sorry, but I just don’t understand how modules form an API boundary
>> in this system.  To me a boundary means something that blocks access.  In
>> this system `internal` ranges over the entire module and all submodules.
>> The only boundaries I can see besides the module itself are files and
>> lexical scopes (with `fileprivate` and `private`).
>>
>>
>> A module is a named region that introduces a lexical scope into which
>> declarations may be nested. The name of the module can be used to access
>> these member declarations. A module, like other aggregate structures in
>> Swift, may be extended with new declarations over one or more translation
>> units (files).
>>
>>
>> Your API boundary lives, as it does today, at the edges of each
>> (sub)module declaration.  APIs that are public or open in a module defines
>> code that is free to move across this boundary and into the open.  APIs
>> that are internal are free to have their modules unsealed into other
>> internal modules to enable modular composition.  APIs that are private and
>> fileprivate do not participate in the API boundary because they are not
>> eligible for any kind of export.
>>
>> If any of that is unclear, please let me know.
>>
>>
>> Yes, in fact parts are unclear.
>>
>> "APIs that are public or open in a module defines code that is free to
>> move across this boundary and into the open"
>>
>> This is unclear because you're saying submodules form an API boundary and
>> you're also saying we need 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-03-02 Thread Matthew Johnson via swift-evolution


Sent from my iPad

> On Mar 2, 2017, at 9:06 PM, T.J. Usiyan  wrote:
> 
> +1 overall. prefer this approach over the "scope based" approach in the other 
> proposal

Can you elaborate?  What problems are you hoping submodules will address?

> 
>> On Wed, Feb 22, 2017 at 10:10 AM, Matthew Johnson via swift-evolution 
>>  wrote:
>> 
 On Feb 21, 2017, at 11:54 PM, Robert Widmann  
 wrote:
 
 
 On Feb 22, 2017, at 12:41 AM, Matthew Johnson  
 wrote:
 
 
 
 Sent from my iPad
 
> On Feb 21, 2017, at 11:09 PM, Robert Widmann  
> wrote:
> 
> 
>>> On Feb 21, 2017, at 11:59 PM, Matthew Johnson  
>>> wrote:
>>> 
>>> 
>>> On Feb 21, 2017, at 10:41 PM, Robert Widmann  
>>> wrote:
>>> 
>>> By API boundaries I mean both the one internal to MyModule.Foo and the 
>>> one defined by MyModule.  Here “the API boundary” is explicitly about 
>>> the submodule MyModule.Foo, whose internal state may have been 
>>> “unsealed” in the top level by the extension, but has not been 
>>> re-exported.
>> 
>> I’m sorry, but I just don’t understand how modules form an API boundary 
>> in this system.  To me a boundary means something that blocks access.  
>> In this system `internal` ranges over the entire module and all 
>> submodules.  The only boundaries I can see besides the module itself are 
>> files and lexical scopes (with `fileprivate` and `private`).  
>> 
> 
> A module is a named region that introduces a lexical scope into which 
> declarations may be nested. The name of the module can be used to access 
> these member declarations. A module, like other aggregate structures in 
> Swift, may be extended with new declarations over one or more translation 
> units (files).
> 
> 
> Your API boundary lives, as it does today, at the edges of each 
> (sub)module declaration.  APIs that are public or open in a module 
> defines code that is free to move across this boundary and into the open. 
>  APIs that are internal are free to have their modules unsealed into 
> other internal modules to enable modular composition.  APIs that are 
> private and fileprivate do not participate in the API boundary because 
> they are not eligible for any kind of export.  
> 
> If any of that is unclear, please let me know. 
 
 Yes, in fact parts are unclear.
 
 "APIs that are public or open in a module defines code that is free to 
 move across this boundary and into the open"
 
 This is unclear because you're saying submodules form an API boundary and 
 you're also saying we need to make APIs open or public to allow them to 
 move across this boundary.  But then you say we can unseal it (import or 
 extend, right?) within the module and gain visibility to the internal 
 symbols.  Are you trying to say that it's a soft boundary within the 
 module that can be permeated with an import or by extension?
>>> 
>>> Of course.  Soft implies more permeability than you are actually afforded, 
>>> but if you want to think of it that way then it may help to put it in 
>>> context.  
>>> 
>>> For what it’s worth, the bulk of the discussion around this feature is 
>>> focused on author-side concerns like the behavior of internal modules 
>>> because access control makes a mess of any reasonable semantics. 
>>> 
 
 If so, that's not the kind of boundary I think many of us are talking 
 about.  We're talking about a hard boundary within the module, but broader 
 than a file.
>>> 
>>> How then, does one go about accessing declarations contained in these kinds 
>>> of impermeable modules?  You must define points of exposure to be able to 
>>> use the module.  What you’re describing is as though you had can only build 
>>> hierarchies of completely private types and then cherry-pick them 
>>> one-by-one into the open - which, mind you, is not a pattern encouraged by 
>>> any of the access control levels we have today and isn’t supported by any 
>>> language I’m aware of.
>> 
>> There are ways to do this without requiring cherry picking individual types. 
>>  I’m not looking for impermeable modules.  I’m looking for bounded 
>> visibility within the module in a way that is very similar to `fileprivate`, 
>> but at a larger granularity.  I’m writing up my view of submodules so we 
>> have something more concrete to discuss.
>> 
>>> 
 
>>  means that it is trivial to put code anywhere within the module that 
>> extends the submodule and wraps a symbol in a new name and declares it 
>> `public`.  
> 
> Precisely.  That’s the same pattern that good Swift code, arguably good 
> code in any language that enables 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-03-02 Thread T.J. Usiyan via swift-evolution
+1 overall. prefer this approach over the "scope based" approach in the
other proposal

On Wed, Feb 22, 2017 at 10:10 AM, Matthew Johnson via swift-evolution <
swift-evolution@swift.org> wrote:

>
> On Feb 21, 2017, at 11:54 PM, Robert Widmann 
> wrote:
>
>
> On Feb 22, 2017, at 12:41 AM, Matthew Johnson 
> wrote:
>
>
>
> Sent from my iPad
>
> On Feb 21, 2017, at 11:09 PM, Robert Widmann 
> wrote:
>
>
> On Feb 21, 2017, at 11:59 PM, Matthew Johnson 
> wrote:
>
>
> On Feb 21, 2017, at 10:41 PM, Robert Widmann 
> wrote:
>
> By API boundaries I mean both the one internal to MyModule.Foo and the one
> defined by MyModule.  Here “the API boundary” is explicitly about the
> submodule MyModule.Foo, whose internal state may have been “unsealed” in
> the top level by the extension, but has not been re-exported.
>
>
> I’m sorry, but I just don’t understand how modules form an API boundary in
> this system.  To me a boundary means something that blocks access.  In this
> system `internal` ranges over the entire module and all submodules.  The
> only boundaries I can see besides the module itself are files and lexical
> scopes (with `fileprivate` and `private`).
>
>
> A module is a named region that introduces a lexical scope into which
> declarations may be nested. The name of the module can be used to access
> these member declarations. A module, like other aggregate structures in
> Swift, may be extended with new declarations over one or more translation
> units (files).
>
>
> Your API boundary lives, as it does today, at the edges of each
> (sub)module declaration.  APIs that are public or open in a module defines
> code that is free to move across this boundary and into the open.  APIs
> that are internal are free to have their modules unsealed into other
> internal modules to enable modular composition.  APIs that are private and
> fileprivate do not participate in the API boundary because they are not
> eligible for any kind of export.
>
> If any of that is unclear, please let me know.
>
>
> Yes, in fact parts are unclear.
>
> "APIs that are public or open in a module defines code that is free to
> move across this boundary and into the open"
>
> This is unclear because you're saying submodules form an API boundary and
> you're also saying we need to make APIs open or public to allow them to
> move across this boundary.  But then you say we can unseal it (import or
> extend, right?) within the module and gain visibility to the internal
> symbols.  Are you trying to say that it's a soft boundary within the module
> that can be permeated with an import or by extension?
>
>
> Of course.  *Soft* implies more permeability than you are actually
> afforded, but if you want to think of it that way then it may help to put
> it in context.
>
> For what it’s worth, the bulk of the discussion around this feature is
> focused on author-side concerns like the behavior of internal modules
> because access control makes a mess of any reasonable semantics.
>
>
> If so, that's not the kind of boundary I think many of us are talking
> about.  We're talking about a hard boundary within the module, but broader
> than a file.
>
>
> How then, does one go about accessing declarations contained in these
> kinds of impermeable modules?  You *must* define points of exposure to be
> able to use the module.  What you’re describing is as though you had can
> only build hierarchies of completely private types and then cherry-pick
> them one-by-one into the open - which, mind you, is not a pattern
> encouraged by any of the access control levels we have today and isn’t
> supported by any language I’m aware of.
>
>
> There are ways to do this without requiring cherry picking individual
> types.  I’m not looking for impermeable modules.  I’m looking for bounded
> visibility within the module in a way that is very similar to
> `fileprivate`, but at a larger granularity.  I’m writing up my view of
> submodules so we have something more concrete to discuss.
>
>
>
>  means that it is trivial to put code anywhere within the module that
> extends the submodule and wraps a symbol in a new name and declares it
> `public`.
>
>
> Precisely.  That’s the same pattern that good Swift code, arguably good
> code in any language that enables hiding, uses today.
>
> They can also trivially add a `public import MyModule.Foo` anywhere at the
> top level of their file because *every* file is forced to include top
> level scope.
>
>
> Perhaps you misunderstand.  Say the APIs in MyModule.Foo were all of
> internal or stricter access: The re-export is a no-op.  You *cannot* change
> the access level of declarations, you can only do the modular thing and
> wrap them in a palatable interface for export by a module you want to be
> user-facing.  You have to *decide* to make an API public, just as today
> you have to decide to make part of an 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-22 Thread Matthew Johnson via swift-evolution

> On Feb 21, 2017, at 11:54 PM, Robert Widmann  wrote:
> 
> 
>> On Feb 22, 2017, at 12:41 AM, Matthew Johnson > > wrote:
>> 
>> 
>> 
>> Sent from my iPad
>> 
>> On Feb 21, 2017, at 11:09 PM, Robert Widmann > > wrote:
>> 
>>> 
 On Feb 21, 2017, at 11:59 PM, Matthew Johnson > wrote:
 
 
> On Feb 21, 2017, at 10:41 PM, Robert Widmann  > wrote:
> 
> By API boundaries I mean both the one internal to MyModule.Foo and the 
> one defined by MyModule.  Here “the API boundary” is explicitly about the 
> submodule MyModule.Foo, whose internal state may have been “unsealed” in 
> the top level by the extension, but has not been re-exported.
 
 I’m sorry, but I just don’t understand how modules form an API boundary in 
 this system.  To me a boundary means something that blocks access.  In 
 this system `internal` ranges over the entire module and all submodules.  
 The only boundaries I can see besides the module itself are files and 
 lexical scopes (with `fileprivate` and `private`).  
 
>>> 
>>> A module is a named region that introduces a lexical scope into which 
>>> declarations may be nested. The name of the module can be used to access 
>>> these member declarations. A module, like other aggregate structures in 
>>> Swift, may be extended with new declarations over one or more translation 
>>> units (files).
>>> 
>>> 
>>> Your API boundary lives, as it does today, at the edges of each (sub)module 
>>> declaration.  APIs that are public or open in a module defines code that is 
>>> free to move across this boundary and into the open.  APIs that are 
>>> internal are free to have their modules unsealed into other internal 
>>> modules to enable modular composition.  APIs that are private and 
>>> fileprivate do not participate in the API boundary because they are not 
>>> eligible for any kind of export.  
>>> 
>>> If any of that is unclear, please let me know. 
>> 
>> Yes, in fact parts are unclear.
>> 
>> "APIs that are public or open in a module defines code that is free to move 
>> across this boundary and into the open"
>> 
>> This is unclear because you're saying submodules form an API boundary and 
>> you're also saying we need to make APIs open or public to allow them to move 
>> across this boundary.  But then you say we can unseal it (import or extend, 
>> right?) within the module and gain visibility to the internal symbols.  Are 
>> you trying to say that it's a soft boundary within the module that can be 
>> permeated with an import or by extension?
> 
> Of course.  Soft implies more permeability than you are actually afforded, 
> but if you want to think of it that way then it may help to put it in 
> context.  
> 
> For what it’s worth, the bulk of the discussion around this feature is 
> focused on author-side concerns like the behavior of internal modules because 
> access control makes a mess of any reasonable semantics. 
> 
>> 
>> If so, that's not the kind of boundary I think many of us are talking about. 
>>  We're talking about a hard boundary within the module, but broader than a 
>> file.
> 
> How then, does one go about accessing declarations contained in these kinds 
> of impermeable modules?  You must define points of exposure to be able to use 
> the module.  What you’re describing is as though you had can only build 
> hierarchies of completely private types and then cherry-pick them one-by-one 
> into the open - which, mind you, is not a pattern encouraged by any of the 
> access control levels we have today and isn’t supported by any language I’m 
> aware of.

There are ways to do this without requiring cherry picking individual types.  
I’m not looking for impermeable modules.  I’m looking for bounded visibility 
within the module in a way that is very similar to `fileprivate`, but at a 
larger granularity.  I’m writing up my view of submodules so we have something 
more concrete to discuss.

> 
>> 
  means that it is trivial to put code anywhere within the module that 
 extends the submodule and wraps a symbol in a new name and declares it 
 `public`. 
>>> 
>>> Precisely.  That’s the same pattern that good Swift code, arguably good 
>>> code in any language that enables hiding, uses today.
>>> 
 They can also trivially add a `public import MyModule.Foo` anywhere at the 
 top level of their file because every file is forced to include top level 
 scope.
>>> 
>>> Perhaps you misunderstand.  Say the APIs in MyModule.Foo were all of 
>>> internal or stricter access: The re-export is a no-op.  You cannot change 
>>> the access level of declarations, you can only do the modular thing and 
>>> wrap them in a palatable interface for 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Robert Widmann via swift-evolution

> On Feb 22, 2017, at 12:41 AM, Matthew Johnson  wrote:
> 
> 
> 
> Sent from my iPad
> 
> On Feb 21, 2017, at 11:09 PM, Robert Widmann  > wrote:
> 
>> 
>>> On Feb 21, 2017, at 11:59 PM, Matthew Johnson >> > wrote:
>>> 
>>> 
 On Feb 21, 2017, at 10:41 PM, Robert Widmann > wrote:
 
 By API boundaries I mean both the one internal to MyModule.Foo and the one 
 defined by MyModule.  Here “the API boundary” is explicitly about the 
 submodule MyModule.Foo, whose internal state may have been “unsealed” in 
 the top level by the extension, but has not been re-exported.
>>> 
>>> I’m sorry, but I just don’t understand how modules form an API boundary in 
>>> this system.  To me a boundary means something that blocks access.  In this 
>>> system `internal` ranges over the entire module and all submodules.  The 
>>> only boundaries I can see besides the module itself are files and lexical 
>>> scopes (with `fileprivate` and `private`).  
>>> 
>> 
>> A module is a named region that introduces a lexical scope into which 
>> declarations may be nested. The name of the module can be used to access 
>> these member declarations. A module, like other aggregate structures in 
>> Swift, may be extended with new declarations over one or more translation 
>> units (files).
>> 
>> 
>> Your API boundary lives, as it does today, at the edges of each (sub)module 
>> declaration.  APIs that are public or open in a module defines code that is 
>> free to move across this boundary and into the open.  APIs that are internal 
>> are free to have their modules unsealed into other internal modules to 
>> enable modular composition.  APIs that are private and fileprivate do not 
>> participate in the API boundary because they are not eligible for any kind 
>> of export.  
>> 
>> If any of that is unclear, please let me know. 
> 
> Yes, in fact parts are unclear.
> 
> "APIs that are public or open in a module defines code that is free to move 
> across this boundary and into the open"
> 
> This is unclear because you're saying submodules form an API boundary and 
> you're also saying we need to make APIs open or public to allow them to move 
> across this boundary.  But then you say we can unseal it (import or extend, 
> right?) within the module and gain visibility to the internal symbols.  Are 
> you trying to say that it's a soft boundary within the module that can be 
> permeated with an import or by extension?

Of course.  Soft implies more permeability than you are actually afforded, but 
if you want to think of it that way then it may help to put it in context.  

For what it’s worth, the bulk of the discussion around this feature is focused 
on author-side concerns like the behavior of internal modules because access 
control makes a mess of any reasonable semantics. 

> 
> If so, that's not the kind of boundary I think many of us are talking about.  
> We're talking about a hard boundary within the module, but broader than a 
> file.

How then, does one go about accessing declarations contained in these kinds of 
impermeable modules?  You must define points of exposure to be able to use the 
module.  What you’re describing is as though you had can only build hierarchies 
of completely private types and then cherry-pick them one-by-one into the open 
- which, mind you, is not a pattern encouraged by any of the access control 
levels we have today and isn’t supported by any language I’m aware of.

> 
>>>  means that it is trivial to put code anywhere within the module that 
>>> extends the submodule and wraps a symbol in a new name and declares it 
>>> `public`.  
>> 
>> Precisely.  That’s the same pattern that good Swift code, arguably good code 
>> in any language that enables hiding, uses today.
>> 
>>> They can also trivially add a `public import MyModule.Foo` anywhere at the 
>>> top level of their file because every file is forced to include top level 
>>> scope.
>> 
>> Perhaps you misunderstand.  Say the APIs in MyModule.Foo were all of 
>> internal or stricter access: The re-export is a no-op.  You cannot change 
>> the access level of declarations, you can only do the modular thing and wrap 
>> them in a palatable interface for export by a module you want to be 
>> user-facing.  You have to decide to make an API public, just as today you 
>> have to decide to make part of an interface public.  I don’t see how this is 
>> distinct from the goals of this proposal.
> 
> Yes, I understand this.  But submodules aren't visible outside the module by 
> default.  It's possible for a submodule to have public and open symbols 
> without the top level public import anywhere in the program.  

> What I'm saying here is that someone in a distant part of the code base could 
> arbitrarily add it if they 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Matthew Johnson via swift-evolution


Sent from my iPad

> On Feb 21, 2017, at 11:09 PM, Robert Widmann  wrote:
> 
> 
>>> On Feb 21, 2017, at 11:59 PM, Matthew Johnson  
>>> wrote:
>>> 
>>> 
>>> On Feb 21, 2017, at 10:41 PM, Robert Widmann  
>>> wrote:
>>> 
>>> By API boundaries I mean both the one internal to MyModule.Foo and the one 
>>> defined by MyModule.  Here “the API boundary” is explicitly about the 
>>> submodule MyModule.Foo, whose internal state may have been “unsealed” in 
>>> the top level by the extension, but has not been re-exported.
>> 
>> I’m sorry, but I just don’t understand how modules form an API boundary in 
>> this system.  To me a boundary means something that blocks access.  In this 
>> system `internal` ranges over the entire module and all submodules.  The 
>> only boundaries I can see besides the module itself are files and lexical 
>> scopes (with `fileprivate` and `private`).  
>> 
> 
> A module is a named region that introduces a lexical scope into which 
> declarations may be nested. The name of the module can be used to access 
> these member declarations. A module, like other aggregate structures in 
> Swift, may be extended with new declarations over one or more translation 
> units (files).
> 
> 
> Your API boundary lives, as it does today, at the edges of each (sub)module 
> declaration.  APIs that are public or open in a module defines code that is 
> free to move across this boundary and into the open.  APIs that are internal 
> are free to have their modules unsealed into other internal modules to enable 
> modular composition.  APIs that are private and fileprivate do not 
> participate in the API boundary because they are not eligible for any kind of 
> export.  
> 
> If any of that is unclear, please let me know. 

Yes, in fact parts are unclear.

"APIs that are public or open in a module defines code that is free to move 
across this boundary and into the open"

This is unclear because you're saying submodules form an API boundary and 
you're also saying we need to make APIs open or public to allow them to move 
across this boundary.  But then you say we can unseal it (import or extend, 
right?) within the module and gain visibility to the internal symbols.  Are you 
trying to say that it's a soft boundary within the module that can be permeated 
with an import or by extension?

If so, that's not the kind of boundary I think many of us are talking about.  
We're talking about a hard boundary within the module, but broader than a file.

>>  means that it is trivial to put code anywhere within the module that 
>> extends the submodule and wraps a symbol in a new name and declares it 
>> `public`.  
> 
> Precisely.  That’s the same pattern that good Swift code, arguably good code 
> in any language that enables hiding, uses today.
> 
>> They can also trivially add a `public import MyModule.Foo` anywhere at the 
>> top level of their file because every file is forced to include top level 
>> scope.
> 
> Perhaps you misunderstand.  Say the APIs in MyModule.Foo were all of internal 
> or stricter access: The re-export is a no-op.  You cannot change the access 
> level of declarations, you can only do the modular thing and wrap them in a 
> palatable interface for export by a module you want to be user-facing.  You 
> have to decide to make an API public, just as today you have to decide to 
> make part of an interface public.  I don’t see how this is distinct from the 
> goals of this proposal.

Yes, I understand this.  But submodules aren't visible outside the module by 
default.  It's possible for a submodule to have public and open symbols without 
the top level public import anywhere in the program.  What I'm saying here is 
that someone in a distant part of the code base could arbitrarily add it if 
they decided to.  The system doesn't prevent it.  

I understand that you consider that a non goal.  I'm simply pointing out that 
the system has this property.  I think it's reasonable to want a system with 
different properties.  And I don't think it's clear yet exactly what kind of 
system might garner the support necessary to be accepted as Swift's submodule 
system.  That's part of the reason we have these discussions! :)

> 
>> 
>> In my opinion, we need to identify what goals we have for a submodule system 
>> - what problems are we trying to solve and what use cases do we intend to 
>> enable.  
>> 
>> There are quite a few of us who want the ability to form solid API 
>> boundaries inside a module and view this as one of the fundamental features 
>> of a submodule system.  It’s reasonable to ask why we view this capability 
>> as essential.
>> 
>> I can’t speak for anyone else, but here are a few reasons why it’s important 
>> to me:
>> 
>> * Solid API boundaries are essential to good design.  
>> * Having access to an entire code base does not reduce the benefits of #1.  
>> Some code bases are substantial in size 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Robert Widmann via swift-evolution

> On Feb 21, 2017, at 11:59 PM, Matthew Johnson  wrote:
> 
> 
>> On Feb 21, 2017, at 10:41 PM, Robert Widmann > > wrote:
>> 
>> By API boundaries I mean both the one internal to MyModule.Foo and the one 
>> defined by MyModule.  Here “the API boundary” is explicitly about the 
>> submodule MyModule.Foo, whose internal state may have been “unsealed” in the 
>> top level by the extension, but has not been re-exported.
> 
> I’m sorry, but I just don’t understand how modules form an API boundary in 
> this system.  To me a boundary means something that blocks access.  In this 
> system `internal` ranges over the entire module and all submodules.  The only 
> boundaries I can see besides the module itself are files and lexical scopes 
> (with `fileprivate` and `private`).  
> 

A module is a named region that introduces a lexical scope into which 
declarations may be nested. The name of the module can be used to access these 
member declarations. A module, like other aggregate structures in Swift, may be 
extended with new declarations over one or more translation units (files).


Your API boundary lives, as it does today, at the edges of each (sub)module 
declaration.  APIs that are public or open in a module defines code that is 
free to move across this boundary and into the open.  APIs that are internal 
are free to have their modules unsealed into other internal modules to enable 
modular composition.  APIs that are private and fileprivate do not participate 
in the API boundary because they are not eligible for any kind of export.  

If any of that is unclear, please let me know. 

> This means that it is trivial to put code anywhere within the module that 
> extends the submodule and wraps a symbol in a new name and declares it 
> `public`.  

Precisely.  That’s the same pattern that good Swift code, arguably good code in 
any language that enables hiding, uses today.

> They can also trivially add a `public import MyModule.Foo` anywhere at the 
> top level of their file because every file is forced to include top level 
> scope.

Perhaps you misunderstand.  Say the APIs in MyModule.Foo were all of internal 
or stricter access: The re-export is a no-op.  You cannot change the access 
level of declarations, you can only do the modular thing and wrap them in a 
palatable interface for export by a module you want to be user-facing.  You 
have to decide to make an API public, just as today you have to decide to make 
part of an interface public.  I don’t see how this is distinct from the goals 
of this proposal.

> 
> In my opinion, we need to identify what goals we have for a submodule system 
> - what problems are we trying to solve and what use cases do we intend to 
> enable.  
> 
> There are quite a few of us who want the ability to form solid API boundaries 
> inside a module and view this as one of the fundamental features of a 
> submodule system.  It’s reasonable to ask why we view this capability as 
> essential.
> 
> I can’t speak for anyone else, but here are a few reasons why it’s important 
> to me:
> 
> * Solid API boundaries are essential to good design.  
> * Having access to an entire code base does not reduce the benefits of #1.  
> Some code bases are substantial in size and hard boundaries are important to 
> keeping them manageable.
> * Using full-fledged modules to do this is possible, but also involves a bit 
> of ceremony that is incidental, not essential complexity in many cases.  It 
> would be better to have a lighter weight mechanism to do this.
> * Swift currently only has whole module optimization, not whole program 
> optimization.  There is a performance penalty to using full-fledged modules.
> 
>> 
>> ~Robert Widmann
>> 
>>> On Feb 21, 2017, at 11:38 PM, Matthew Johnson >> > wrote:
>>> 
>>> 
 On Feb 21, 2017, at 10:29 PM, Robert Widmann > wrote:
 
 This level of access, the “private to this submodule except to the select 
 set of interfaces I want to see it” level, is the equivalent of friend 
 classes in C++.  I don’t consider leaving this out to be a hole, nor is it 
 an "encapsulation-related problem” because at no point can you break the 
 API boundary and re-export anything here with a higher level of access 
 than it had previously.
>>> 
>>> By API boundary you mean the top-level module, right?
>>> 
 
> On Feb 21, 2017, at 11:13 PM, Matthew Johnson  > wrote:
> 
> 
>> On Feb 21, 2017, at 10:11 PM, Matthew Johnson > > wrote:
>> 
>> 
>>> On Feb 21, 2017, at 9:47 PM, Brent Royal-Gordon via swift-evolution 
>>> > wrote:

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Matthew Johnson via swift-evolution

> On Feb 21, 2017, at 10:41 PM, Robert Widmann  wrote:
> 
> By API boundaries I mean both the one internal to MyModule.Foo and the one 
> defined by MyModule.  Here “the API boundary” is explicitly about the 
> submodule MyModule.Foo, whose internal state may have been “unsealed” in the 
> top level by the extension, but has not been re-exported.

I’m sorry, but I just don’t understand how modules form an API boundary in this 
system.  To me a boundary means something that blocks access.  In this system 
`internal` ranges over the entire module and all submodules.  The only 
boundaries I can see besides the module itself are files and lexical scopes 
(with `fileprivate` and `private`).  

This means that it is trivial to put code anywhere within the module that 
extends the submodule and wraps a symbol in a new name and declares it 
`public`.  They can also trivially add a `public import MyModule.Foo` anywhere 
at the top level of their file because every file is forced to include top 
level scope.

In my opinion, we need to identify what goals we have for a submodule system - 
what problems are we trying to solve and what use cases do we intend to enable. 
 

There are quite a few of us who want the ability to form solid API boundaries 
inside a module and view this as one of the fundamental features of a submodule 
system.  It’s reasonable to ask why we view this capability as essential.

I can’t speak for anyone else, but here are a few reasons why it’s important to 
me:

* Solid API boundaries are essential to good design.  
* Having access to an entire code base does not reduce the benefits of #1.  
Some code bases are substantial in size and hard boundaries are important to 
keeping them manageable.
* Using full-fledged modules to do this is possible, but also involves a bit of 
ceremony that is incidental, not essential complexity in many cases.  It would 
be better to have a lighter weight mechanism to do this.
* Swift currently only has whole module optimization, not whole program 
optimization.  There is a performance penalty to using full-fledged modules.

> 
> ~Robert Widmann
> 
>> On Feb 21, 2017, at 11:38 PM, Matthew Johnson  wrote:
>> 
>> 
>>> On Feb 21, 2017, at 10:29 PM, Robert Widmann  
>>> wrote:
>>> 
>>> This level of access, the “private to this submodule except to the select 
>>> set of interfaces I want to see it” level, is the equivalent of friend 
>>> classes in C++.  I don’t consider leaving this out to be a hole, nor is it 
>>> an "encapsulation-related problem” because at no point can you break the 
>>> API boundary and re-export anything here with a higher level of access than 
>>> it had previously.
>> 
>> By API boundary you mean the top-level module, right?
>> 
>>> 
 On Feb 21, 2017, at 11:13 PM, Matthew Johnson  
 wrote:
 
 
> On Feb 21, 2017, at 10:11 PM, Matthew Johnson  
> wrote:
> 
> 
>> On Feb 21, 2017, at 9:47 PM, Brent Royal-Gordon via swift-evolution 
>>  wrote:
>> 
>>> On Feb 21, 2017, at 7:38 PM, Robert Widmann  
>>> wrote:
>>> 
>>> Correct.  Because, in dividing the submodule across an extension, you 
>>> have placed what should be a private API into a differently-scoped 
>>> location.
>> 
>> Okay. So is your submodule design not intended to address the "I want to 
>> encapsulate implementation details so they're only visible to several 
>> units of code in different files, but not the entire module" use case? 
>> Because if there's no way to scope a symbol to "everything inside this 
>> submodule, but nothing outside this submodule", I think it leaves that 
>> use case unserved.
> 
> Unless I’m missing something there is also another encapsulation-related 
> problem with the proposed design.  Let’s suppose for the sake of 
> discussion there was a `submoduleprivate` access modifier (intentionally 
> ungainly and not realistic).
> 
> // File 1
> module Foo {
> // internal, visible to the whole module
> class Bar { submoduleprivate var protectedState: Int = 0 }
> }
> 
> // File 2 - Has nothing to do with Foo at all
> import MyModule.Foo
> 
> module NotFoo {
> // Hey, I need to see Bar.protectedState!!!
> func totallyNotFoo() {
>   var bar = Bar()
>   bar.foosExposedPrivates = 42
> }
> }
> 
> // ok, I’ll just add an extension to Foo so I can see submoduleprivate 
> and wrap what I need
> module Foo {
 
 Oops, this should have been `extension Foo`, but otherwise I believe it is 
 valid under this proposal.
 
> // Hey, I’ll be nice and keep it fileprivate, but I could make it public 
> if I wanted to.
> extension Foo {
> fileprivate var foosExposedPrivates: 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Robert Widmann via swift-evolution
Then let’s discuss that.

You claim Swift has some emphasis on file-oriented programming constructs, I 
argue this is the case locally (fileprivate), but not the case in the language 
as a whole.  Looking more broadly, it is possible to restrict yourself to a 
particular view where one public type resides in one file, but then what to 
make of extensions?  What becomes of “internal” access, which permeates the 
entire module crossing over any file boundaries that might exist?  Today, a 
Swift module can depend on the kinds of files given to the compiler, but there 
is particular emphasis on a module not necessarily being a collection of files, 
but a collection of interfaces all living under the same shared namespace (the 
module name).  A particular facet of that interface set may be freely extended 
by the presence, or contracted by the absence, of a file or files when the 
module is built but one could very well imagine alternative abstractions that 
would serve this purpose just as well - e.g. an in-memory AST.

Maybe what you notice is that you are encouraged (or rather, required) by your 
tools to organize your code a particular way, and this is no mistake.  They 
exist apart from the language itself for a reason, because they themselves 
often depend on the state of the filesystem or the outside world and that 
concern spills over (correctly or not) into your organizational style.  But 
organizational style is just that: we can enable a broader class of programs to 
be designed with the system given here than with one that restricts us to a 
subset of it.  Because let’s not forget, it is actually a subset of the 
functionality presented herein.  If the proposal’s were implemented today, you 
would absolutely be able to design these kinds of modules and tie them to 
filesystem locations.  But you would also be free to group functionality and 
tie a set of files together into the same (sub)module.

> On Feb 21, 2017, at 10:46 PM, Xiaodi Wu  wrote:
> 
> Well put. As for me, it is not the syntactic delta with which I am concerned. 
> It is just a canary for the organizational delta.
> 
> There are certain freedoms enabled not by the _lack_ of constraints but 
> rather their judicious application. Swift has in the past--and it is your 
> burden to justify why it shouldn't continue to in the future--judged the 
> file-based approach to be one such judicious constraint.
> 
> 
> On Tue, Feb 21, 2017 at 21:42 Robert Widmann  > wrote:
>> On Feb 21, 2017, at 10:36 PM, Matthew Johnson > > wrote:
>> 
>>> 
>>> On Feb 21, 2017, at 9:28 PM, Robert Widmann via swift-evolution 
>>> > wrote:
>>> 
 
 On Feb 21, 2017, at 10:03 PM, Xiaodi Wu > wrote:
 
 On Tue, Feb 21, 2017 at 8:41 PM, Robert Widmann >wrote:
 
> On Feb 21, 2017, at 9:37 PM, Xiaodi Wu  > wrote:
> 
> On Tue, Feb 21, 2017 at 8:22 PM, Robert Widmann  >wrote:
> 
>> On Feb 21, 2017, at 9:13 PM, Xiaodi Wu > > wrote:
>> 
>> On Tue, Feb 21, 2017 at 7:59 PM, Robert Widmann via swift-evolution 
>> > wrote:
>> 
>>> On Feb 21, 2017, at 7:36 PM, Nevin Brackett-Rozinsky via 
>>> swift-evolution >> > wrote:
>>> 
>>> To my mind, any submodule system for Swift should be designed to 
>>> relieve the pressure for long files, and make it easy to group tightly 
>>> related files into a single unit with shared visibility. That way 
>>> developers can easily organize their code into smaller files while 
>>> utilizing Swift’s pattern of providing protocol conformances in 
>>> extensions and keeping implementation details hidden from the rest of 
>>> the module at large.
>>> 
>> 
>> Wonderful, because that’s absolutely supported by this proposal.  To 
>> group tightly related files into a single unit, simply declare a 
>> submodule for them and extend it in each of your related files.
>> 
>> It's supported, but it isn't first-class. By this I mean: there are two 
>> distinguishable uses supported by your proposal, lumped together by the 
>> fact that they are both about grouping units of code together. Put 
>> crudely, one use case is grouping lines of code, while the other is 
>> about grouping files of code. The merits of supporting both have already 
>> been debated in this discussion. The issue I'll touch on is supporting 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Robert Widmann via swift-evolution
By API boundaries I mean both the one internal to MyModule.Foo and the one 
defined by MyModule.  Here “the API boundary” is explicitly about the submodule 
MyModule.Foo, whose internal state may have been “unsealed” in the top level by 
the extension, but has not been re-exported.

~Robert Widmann

> On Feb 21, 2017, at 11:38 PM, Matthew Johnson  wrote:
> 
> 
>> On Feb 21, 2017, at 10:29 PM, Robert Widmann  
>> wrote:
>> 
>> This level of access, the “private to this submodule except to the select 
>> set of interfaces I want to see it” level, is the equivalent of friend 
>> classes in C++.  I don’t consider leaving this out to be a hole, nor is it 
>> an "encapsulation-related problem” because at no point can you break the API 
>> boundary and re-export anything here with a higher level of access than it 
>> had previously.
> 
> By API boundary you mean the top-level module, right?
> 
>> 
>>> On Feb 21, 2017, at 11:13 PM, Matthew Johnson  
>>> wrote:
>>> 
>>> 
 On Feb 21, 2017, at 10:11 PM, Matthew Johnson  
 wrote:
 
 
> On Feb 21, 2017, at 9:47 PM, Brent Royal-Gordon via swift-evolution 
>  wrote:
> 
>> On Feb 21, 2017, at 7:38 PM, Robert Widmann  
>> wrote:
>> 
>> Correct.  Because, in dividing the submodule across an extension, you 
>> have placed what should be a private API into a differently-scoped 
>> location.
> 
> Okay. So is your submodule design not intended to address the "I want to 
> encapsulate implementation details so they're only visible to several 
> units of code in different files, but not the entire module" use case? 
> Because if there's no way to scope a symbol to "everything inside this 
> submodule, but nothing outside this submodule", I think it leaves that 
> use case unserved.
 
 Unless I’m missing something there is also another encapsulation-related 
 problem with the proposed design.  Let’s suppose for the sake of 
 discussion there was a `submoduleprivate` access modifier (intentionally 
 ungainly and not realistic).
 
 // File 1
 module Foo {
 // internal, visible to the whole module
 class Bar { submoduleprivate var protectedState: Int = 0 }
 }
 
 // File 2 - Has nothing to do with Foo at all
 import MyModule.Foo
 
 module NotFoo {
 // Hey, I need to see Bar.protectedState!!!
 func totallyNotFoo() {
var bar = Bar()
bar.foosExposedPrivates = 42
 }
 }
 
 // ok, I’ll just add an extension to Foo so I can see submoduleprivate and 
 wrap what I need
 module Foo {
>>> 
>>> Oops, this should have been `extension Foo`, but otherwise I believe it is 
>>> valid under this proposal.
>>> 
 // Hey, I’ll be nice and keep it fileprivate, but I could make it public 
 if I wanted to.
 extension Foo {
  fileprivate var foosExposedPrivates: Int {
 // Yep, I’m inside Foo so I can see it’s submoduleprivate stuff
 get { return protectedState }
 set  { protectedState = newValue }
  }
 }
 }
 
> 
> -- 
> Brent Royal-Gordon
> Architechies
> 
> ___
> swift-evolution mailing list
> swift-evolution@swift.org
> https://lists.swift.org/mailman/listinfo/swift-evolution
 
>>> 
>> 
> 

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Matthew Johnson via swift-evolution

> On Feb 21, 2017, at 10:29 PM, Robert Widmann  wrote:
> 
> This level of access, the “private to this submodule except to the select set 
> of interfaces I want to see it” level, is the equivalent of friend classes in 
> C++.  I don’t consider leaving this out to be a hole, nor is it an 
> "encapsulation-related problem” because at no point can you break the API 
> boundary and re-export anything here with a higher level of access than it 
> had previously.

By API boundary you mean the top-level module, right?

> 
>> On Feb 21, 2017, at 11:13 PM, Matthew Johnson  wrote:
>> 
>> 
>>> On Feb 21, 2017, at 10:11 PM, Matthew Johnson  
>>> wrote:
>>> 
>>> 
 On Feb 21, 2017, at 9:47 PM, Brent Royal-Gordon via swift-evolution 
  wrote:
 
> On Feb 21, 2017, at 7:38 PM, Robert Widmann  
> wrote:
> 
> Correct.  Because, in dividing the submodule across an extension, you 
> have placed what should be a private API into a differently-scoped 
> location.
 
 Okay. So is your submodule design not intended to address the "I want to 
 encapsulate implementation details so they're only visible to several 
 units of code in different files, but not the entire module" use case? 
 Because if there's no way to scope a symbol to "everything inside this 
 submodule, but nothing outside this submodule", I think it leaves that use 
 case unserved.
>>> 
>>> Unless I’m missing something there is also another encapsulation-related 
>>> problem with the proposed design.  Let’s suppose for the sake of discussion 
>>> there was a `submoduleprivate` access modifier (intentionally ungainly and 
>>> not realistic).
>>> 
>>> // File 1
>>> module Foo {
>>>  // internal, visible to the whole module
>>>  class Bar { submoduleprivate var protectedState: Int = 0 }
>>> }
>>> 
>>> // File 2 - Has nothing to do with Foo at all
>>> import MyModule.Foo
>>> 
>>> module NotFoo {
>>> // Hey, I need to see Bar.protectedState!!!
>>> func totallyNotFoo() {
>>> var bar = Bar()
>>> bar.foosExposedPrivates = 42
>>> }
>>> }
>>> 
>>> // ok, I’ll just add an extension to Foo so I can see submoduleprivate and 
>>> wrap what I need
>>> module Foo {
>> 
>> Oops, this should have been `extension Foo`, but otherwise I believe it is 
>> valid under this proposal.
>> 
>>>  // Hey, I’ll be nice and keep it fileprivate, but I could make it public 
>>> if I wanted to.
>>>  extension Foo {
>>>   fileprivate var foosExposedPrivates: Int {
>>>  // Yep, I’m inside Foo so I can see it’s submoduleprivate stuff
>>>  get { return protectedState }
>>>  set  { protectedState = newValue }
>>>   }
>>>  }
>>> }
>>> 
 
 -- 
 Brent Royal-Gordon
 Architechies
 
 ___
 swift-evolution mailing list
 swift-evolution@swift.org
 https://lists.swift.org/mailman/listinfo/swift-evolution
>>> 
>> 
> 

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Robert Widmann via swift-evolution
TJ and I had a proposal 
 that would 
have closed this loophole by overhauling qualified imports syntax.

> On Feb 21, 2017, at 11:36 PM, Matthew Johnson  wrote:
> 
> 
>> On Feb 21, 2017, at 10:25 PM, Robert Widmann > > wrote:
>> 
>> Good question!  This behavior is actually the behavior that exists today.  
>> For example, open a playground and type
>> 
>> import Foundation.NSDebug
>> 
>> let s : NSString = “"
>> 
>> You’ll notice no matter which submodule you try to visit (Darwin.uuid is 
>> another good example), Swift has decided to insert a top-level import.  We 
>> decided not to change this behavior to maintain source compatibility.
> 
> So there is no way to import a single submodule?  If that is the case why not 
> just disallow the syntax which implies only a single submodule is getting 
> imported and require users to say `import Foo`?  I don’t know what the 
> rationale was for this in the past, but I think it’s undesirable and we’re 
> trying to design something for the future here.
> 
>> 
>> 
>>> On Feb 21, 2017, at 11:21 PM, Matthew Johnson >> > wrote:
>>> 
 
 On Feb 20, 2017, at 7:56 PM, Robert Widmann via swift-evolution 
 > wrote:
 
 Good Evening All,
 
 Jaden Geller and I have been considering a (sub)module system for Swift 
 that would complement the existing language but also provide sorely needed 
 modularity.  A draft of the proposal is attached to this email, but it can 
 also be read as a gist 
  if you 
 desire.
 
 Cheers,
 
 ~Robert Widmann
 
 Modular Swift
 
 Proposal: SE- 
 Authors: Robert Widmann , Jaden Geller 
 
 Review Manager: TBD
 Status: Awaiting review
  
 Introduction
 
 Almost every major programming language supports some form of modular 
 programming through constructs like (sub)modules, packages, or interfaces. 
 Swift, though it provides top-level modules to organize code under, does 
 not provide a complete implementation of any of these concepts, which has 
 led instead to the proliferation of access control levels. This has not 
 proven an effective way to decompose programs into manageable parts, and 
 exposes the need for a real system of modules to solve this modularity 
 problem once and for all.
 
 Separation of code into distinct islands of functionality should be a 
 first-class construct in the language, not dependent on external files and 
 tools or filesystems. To that end, we propose the introduction of a 
 lightweight module system for Swift.
 
 Swift-evolution thread 
 
  
 Motivation
 
 Swift has reached a point in its evolution where rich libraries and large 
 projects that take on many dependencies have matured significantly. To 
 accomodate the information-hiding and semantics-signalling needs of these 
 users at the time, Swift began its access control story with just three 
 access modifiers: public, private, and internal then grew fileprivate and 
 open as the need to express locality of implementation and 
 "subclassability" arose respectively. In doing so, Swift's access control 
 scheme has become anti-modular.
 
  
 Proposed
  solution
 
 We propose the introduction of a lightweight module system for Swift. More 
 than simply namspaces, a module declaration interacts with Swift's access 
 control to provide an API boundary that allows better control over an 
 interface's design.
 
  
 Detailed
  design
 
  
 Syntax
 
 A module is a named region that introduces a lexical scope into which 
 declarations may be nested. The name of the module can be used to access 
 these member declarations. A module, like other aggregate structures in 
 Swift, may be extended with new declarations over one or more translation 
 units (files).
 
 We propose a new declaration kind, module-decl be added to the language. A 
 proposed grammar using the new modulekeyword is given below:
 
 GRAMMAR OF A MODULE DECLARATION

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Matthew Johnson via swift-evolution

> On Feb 21, 2017, at 10:25 PM, Robert Widmann  wrote:
> 
> Good question!  This behavior is actually the behavior that exists today.  
> For example, open a playground and type
> 
> import Foundation.NSDebug
> 
> let s : NSString = “"
> 
> You’ll notice no matter which submodule you try to visit (Darwin.uuid is 
> another good example), Swift has decided to insert a top-level import.  We 
> decided not to change this behavior to maintain source compatibility.

So there is no way to import a single submodule?  If that is the case why not 
just disallow the syntax which implies only a single submodule is getting 
imported and require users to say `import Foo`?  I don’t know what the 
rationale was for this in the past, but I think it’s undesirable and we’re 
trying to design something for the future here.

> 
> 
>> On Feb 21, 2017, at 11:21 PM, Matthew Johnson > > wrote:
>> 
>>> 
>>> On Feb 20, 2017, at 7:56 PM, Robert Widmann via swift-evolution 
>>> > wrote:
>>> 
>>> Good Evening All,
>>> 
>>> Jaden Geller and I have been considering a (sub)module system for Swift 
>>> that would complement the existing language but also provide sorely needed 
>>> modularity.  A draft of the proposal is attached to this email, but it can 
>>> also be read as a gist 
>>>  if you 
>>> desire.
>>> 
>>> Cheers,
>>> 
>>> ~Robert Widmann
>>> 
>>> Modular Swift
>>> 
>>> Proposal: SE- 
>>> Authors: Robert Widmann , Jaden Geller 
>>> 
>>> Review Manager: TBD
>>> Status: Awaiting review
>>>  
>>> Introduction
>>> 
>>> Almost every major programming language supports some form of modular 
>>> programming through constructs like (sub)modules, packages, or interfaces. 
>>> Swift, though it provides top-level modules to organize code under, does 
>>> not provide a complete implementation of any of these concepts, which has 
>>> led instead to the proliferation of access control levels. This has not 
>>> proven an effective way to decompose programs into manageable parts, and 
>>> exposes the need for a real system of modules to solve this modularity 
>>> problem once and for all.
>>> 
>>> Separation of code into distinct islands of functionality should be a 
>>> first-class construct in the language, not dependent on external files and 
>>> tools or filesystems. To that end, we propose the introduction of a 
>>> lightweight module system for Swift.
>>> 
>>> Swift-evolution thread 
>>>  
>>> Motivation
>>> 
>>> Swift has reached a point in its evolution where rich libraries and large 
>>> projects that take on many dependencies have matured significantly. To 
>>> accomodate the information-hiding and semantics-signalling needs of these 
>>> users at the time, Swift began its access control story with just three 
>>> access modifiers: public, private, and internal then grew fileprivate and 
>>> open as the need to express locality of implementation and 
>>> "subclassability" arose respectively. In doing so, Swift's access control 
>>> scheme has become anti-modular.
>>> 
>>>  
>>> Proposed
>>>  solution
>>> 
>>> We propose the introduction of a lightweight module system for Swift. More 
>>> than simply namspaces, a module declaration interacts with Swift's access 
>>> control to provide an API boundary that allows better control over an 
>>> interface's design.
>>> 
>>>  
>>> Detailed
>>>  design
>>> 
>>>  
>>> Syntax
>>> 
>>> A module is a named region that introduces a lexical scope into which 
>>> declarations may be nested. The name of the module can be used to access 
>>> these member declarations. A module, like other aggregate structures in 
>>> Swift, may be extended with new declarations over one or more translation 
>>> units (files).
>>> 
>>> We propose a new declaration kind, module-decl be added to the language. A 
>>> proposed grammar using the new modulekeyword is given below:
>>> 
>>> GRAMMAR OF A MODULE DECLARATION
>>> 
>>> module-declaration -> `module` module-identifier module-body
>>> module-name -> identifier
>>> module-body -> { module-members(opt) }
>>> module-members -> module-member module-members(opt)
>>> module-member -> declaration | compiler-control-statement
>>> GRAMMAR OF A DECLARATION
>>> 
>>> + declaration -> module-declaration
>>>  
>>> 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Robert Widmann via swift-evolution
This level of access, the “private to this submodule except to the select set 
of interfaces I want to see it” level, is the equivalent of friend classes in 
C++.  I don’t consider leaving this out to be a hole, nor is it an 
"encapsulation-related problem” because at no point can you break the API 
boundary and re-export anything here with a higher level of access than it had 
previously.

> On Feb 21, 2017, at 11:13 PM, Matthew Johnson  wrote:
> 
> 
>> On Feb 21, 2017, at 10:11 PM, Matthew Johnson  wrote:
>> 
>> 
>>> On Feb 21, 2017, at 9:47 PM, Brent Royal-Gordon via swift-evolution 
>>>  wrote:
>>> 
 On Feb 21, 2017, at 7:38 PM, Robert Widmann  
 wrote:
 
 Correct.  Because, in dividing the submodule across an extension, you have 
 placed what should be a private API into a differently-scoped location.
>>> 
>>> Okay. So is your submodule design not intended to address the "I want to 
>>> encapsulate implementation details so they're only visible to several units 
>>> of code in different files, but not the entire module" use case? Because if 
>>> there's no way to scope a symbol to "everything inside this submodule, but 
>>> nothing outside this submodule", I think it leaves that use case unserved.
>> 
>> Unless I’m missing something there is also another encapsulation-related 
>> problem with the proposed design.  Let’s suppose for the sake of discussion 
>> there was a `submoduleprivate` access modifier (intentionally ungainly and 
>> not realistic).
>> 
>> // File 1
>> module Foo {
>>   // internal, visible to the whole module
>>   class Bar { submoduleprivate var protectedState: Int = 0 }
>> }
>> 
>> // File 2 - Has nothing to do with Foo at all
>> import MyModule.Foo
>> 
>> module NotFoo {
>>  // Hey, I need to see Bar.protectedState!!!
>>  func totallyNotFoo() {
>>  var bar = Bar()
>>  bar.foosExposedPrivates = 42
>>  }
>> }
>> 
>> // ok, I’ll just add an extension to Foo so I can see submoduleprivate and 
>> wrap what I need
>> module Foo {
> 
> Oops, this should have been `extension Foo`, but otherwise I believe it is 
> valid under this proposal.
> 
>>   // Hey, I’ll be nice and keep it fileprivate, but I could make it public 
>> if I wanted to.
>>   extension Foo {
>>fileprivate var foosExposedPrivates: Int {
>>   // Yep, I’m inside Foo so I can see it’s submoduleprivate stuff
>>   get { return protectedState }
>>   set  { protectedState = newValue }
>>}
>>   }
>> }
>> 
>>> 
>>> -- 
>>> Brent Royal-Gordon
>>> Architechies
>>> 
>>> ___
>>> swift-evolution mailing list
>>> swift-evolution@swift.org
>>> https://lists.swift.org/mailman/listinfo/swift-evolution
>> 
> 

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Robert Widmann via swift-evolution
Good question!  This behavior is actually the behavior that exists today.  For 
example, open a playground and type

import Foundation.NSDebug

let s : NSString = “"

You’ll notice no matter which submodule you try to visit (Darwin.uuid is 
another good example), Swift has decided to insert a top-level import.  We 
decided not to change this behavior to maintain source compatibility.


> On Feb 21, 2017, at 11:21 PM, Matthew Johnson  wrote:
> 
>> 
>> On Feb 20, 2017, at 7:56 PM, Robert Widmann via swift-evolution 
>> > wrote:
>> 
>> Good Evening All,
>> 
>> Jaden Geller and I have been considering a (sub)module system for Swift that 
>> would complement the existing language but also provide sorely needed 
>> modularity.  A draft of the proposal is attached to this email, but it can 
>> also be read as a gist 
>>  if you 
>> desire.
>> 
>> Cheers,
>> 
>> ~Robert Widmann
>> 
>> Modular Swift
>> 
>> Proposal: SE- 
>> Authors: Robert Widmann , Jaden Geller 
>> 
>> Review Manager: TBD
>> Status: Awaiting review
>>  
>> Introduction
>> 
>> Almost every major programming language supports some form of modular 
>> programming through constructs like (sub)modules, packages, or interfaces. 
>> Swift, though it provides top-level modules to organize code under, does not 
>> provide a complete implementation of any of these concepts, which has led 
>> instead to the proliferation of access control levels. This has not proven 
>> an effective way to decompose programs into manageable parts, and exposes 
>> the need for a real system of modules to solve this modularity problem once 
>> and for all.
>> 
>> Separation of code into distinct islands of functionality should be a 
>> first-class construct in the language, not dependent on external files and 
>> tools or filesystems. To that end, we propose the introduction of a 
>> lightweight module system for Swift.
>> 
>> Swift-evolution thread 
>>  
>> Motivation
>> 
>> Swift has reached a point in its evolution where rich libraries and large 
>> projects that take on many dependencies have matured significantly. To 
>> accomodate the information-hiding and semantics-signalling needs of these 
>> users at the time, Swift began its access control story with just three 
>> access modifiers: public, private, and internal then grew fileprivate and 
>> open as the need to express locality of implementation and "subclassability" 
>> arose respectively. In doing so, Swift's access control scheme has become 
>> anti-modular.
>> 
>>  
>> Proposed
>>  solution
>> 
>> We propose the introduction of a lightweight module system for Swift. More 
>> than simply namspaces, a module declaration interacts with Swift's access 
>> control to provide an API boundary that allows better control over an 
>> interface's design.
>> 
>>  
>> Detailed
>>  design
>> 
>>  
>> Syntax
>> 
>> A module is a named region that introduces a lexical scope into which 
>> declarations may be nested. The name of the module can be used to access 
>> these member declarations. A module, like other aggregate structures in 
>> Swift, may be extended with new declarations over one or more translation 
>> units (files).
>> 
>> We propose a new declaration kind, module-decl be added to the language. A 
>> proposed grammar using the new modulekeyword is given below:
>> 
>> GRAMMAR OF A MODULE DECLARATION
>> 
>> module-declaration -> `module` module-identifier module-body
>> module-name -> identifier
>> module-body -> { module-members(opt) }
>> module-members -> module-member module-members(opt)
>> module-member -> declaration | compiler-control-statement
>> GRAMMAR OF A DECLARATION
>> 
>> + declaration -> module-declaration
>>  
>> General
>>  Semantics
>> 
>> Syntax and semantics for imports, as it already supports referencing 
>> submodules imported from C and Objective-C modules, remains unchanged:
>> 
>> // The outermost module is given explicitly 
>> // by passing `-module-name=Foo` or exists implicitly, as today.
>> // module Foo {
>> public class A {}
>> 
>> module Bar {
>>   module Baz {
>> public class C {}
>>   }
>> 
>>   public class B {}
>> }
>> 
>> let message = "Hello, Wisconsin!"
>> // } // End declarations added to module Foo.
>> To consume this interface:
>> 
>> // imports all 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Matthew Johnson via swift-evolution

> On Feb 20, 2017, at 7:56 PM, Robert Widmann via swift-evolution 
>  wrote:
> 
> Good Evening All,
> 
> Jaden Geller and I have been considering a (sub)module system for Swift that 
> would complement the existing language but also provide sorely needed 
> modularity.  A draft of the proposal is attached to this email, but it can 
> also be read as a gist 
>  if you 
> desire.
> 
> Cheers,
> 
> ~Robert Widmann
> 
> Modular Swift
> 
> Proposal: SE- 
> Authors: Robert Widmann , Jaden Geller 
> 
> Review Manager: TBD
> Status: Awaiting review
>  
> Introduction
> 
> Almost every major programming language supports some form of modular 
> programming through constructs like (sub)modules, packages, or interfaces. 
> Swift, though it provides top-level modules to organize code under, does not 
> provide a complete implementation of any of these concepts, which has led 
> instead to the proliferation of access control levels. This has not proven an 
> effective way to decompose programs into manageable parts, and exposes the 
> need for a real system of modules to solve this modularity problem once and 
> for all.
> 
> Separation of code into distinct islands of functionality should be a 
> first-class construct in the language, not dependent on external files and 
> tools or filesystems. To that end, we propose the introduction of a 
> lightweight module system for Swift.
> 
> Swift-evolution thread 
>  
> Motivation
> 
> Swift has reached a point in its evolution where rich libraries and large 
> projects that take on many dependencies have matured significantly. To 
> accomodate the information-hiding and semantics-signalling needs of these 
> users at the time, Swift began its access control story with just three 
> access modifiers: public, private, and internal then grew fileprivate and 
> open as the need to express locality of implementation and "subclassability" 
> arose respectively. In doing so, Swift's access control scheme has become 
> anti-modular.
> 
>  
> Proposed
>  solution
> 
> We propose the introduction of a lightweight module system for Swift. More 
> than simply namspaces, a module declaration interacts with Swift's access 
> control to provide an API boundary that allows better control over an 
> interface's design.
> 
>  
> Detailed
>  design
> 
>  
> Syntax
> 
> A module is a named region that introduces a lexical scope into which 
> declarations may be nested. The name of the module can be used to access 
> these member declarations. A module, like other aggregate structures in 
> Swift, may be extended with new declarations over one or more translation 
> units (files).
> 
> We propose a new declaration kind, module-decl be added to the language. A 
> proposed grammar using the new modulekeyword is given below:
> 
> GRAMMAR OF A MODULE DECLARATION
> 
> module-declaration -> `module` module-identifier module-body
> module-name -> identifier
> module-body -> { module-members(opt) }
> module-members -> module-member module-members(opt)
> module-member -> declaration | compiler-control-statement
> GRAMMAR OF A DECLARATION
> 
> + declaration -> module-declaration
>  
> General
>  Semantics
> 
> Syntax and semantics for imports, as it already supports referencing 
> submodules imported from C and Objective-C modules, remains unchanged:
> 
> // The outermost module is given explicitly 
> // by passing `-module-name=Foo` or exists implicitly, as today.
> // module Foo {
> public class A {}
> 
> module Bar {
>   module Baz {
> public class C {}
>   }
> 
>   public class B {}
> }
> 
> let message = "Hello, Wisconsin!"
> // } // End declarations added to module Foo.
> To consume this interface:
> 
> // imports all of Foo, Foo.Bar, and Foo.Bar.Baz
> import Foo.Bar.Baz
I’ve read this a couple of times now and I keep getting hung up on this.  Is 
the comment a mistake?  I would only expect to get Foo.Bar.Baz here, not 
Foo.Bar or Foo itself.  If it’s not a mistake, why did you choose this behavior?


> 
> // imports Foo.A as A
> import class Foo.A
> // imports Foo.Bar.B as B
> import class Foo.Bar.B
> // imports Foo.Bar.Baz.C as C
> import class Foo.Bar.Baz.C
> A module declaration may only appear as a top-level entity or as a member of 
> another module declaration. The following code is therefore invalid:
> 
> module Foo {
>  

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Matthew Johnson via swift-evolution

> On Feb 21, 2017, at 10:11 PM, Matthew Johnson  wrote:
> 
> 
>> On Feb 21, 2017, at 9:47 PM, Brent Royal-Gordon via swift-evolution 
>>  wrote:
>> 
>>> On Feb 21, 2017, at 7:38 PM, Robert Widmann  
>>> wrote:
>>> 
>>> Correct.  Because, in dividing the submodule across an extension, you have 
>>> placed what should be a private API into a differently-scoped location.
>> 
>> Okay. So is your submodule design not intended to address the "I want to 
>> encapsulate implementation details so they're only visible to several units 
>> of code in different files, but not the entire module" use case? Because if 
>> there's no way to scope a symbol to "everything inside this submodule, but 
>> nothing outside this submodule", I think it leaves that use case unserved.
> 
> Unless I’m missing something there is also another encapsulation-related 
> problem with the proposed design.  Let’s suppose for the sake of discussion 
> there was a `submoduleprivate` access modifier (intentionally ungainly and 
> not realistic).
> 
> // File 1
> module Foo {
>// internal, visible to the whole module
>class Bar { submoduleprivate var protectedState: Int = 0 }
> }
> 
> // File 2 - Has nothing to do with Foo at all
> import MyModule.Foo
> 
> module NotFoo {
>   // Hey, I need to see Bar.protectedState!!!
>   func totallyNotFoo() {
>   var bar = Bar()
>   bar.foosExposedPrivates = 42
>   }
> }
> 
> // ok, I’ll just add an extension to Foo so I can see submoduleprivate and 
> wrap what I need
> module Foo {

Oops, this should have been `extension Foo`, but otherwise I believe it is 
valid under this proposal.

>// Hey, I’ll be nice and keep it fileprivate, but I could make it public 
> if I wanted to.
>extension Bar {
> fileprivate var foosExposedPrivates: Int {
>// Yep, I’m inside Foo so I can see it’s submoduleprivate stuff
>get { return protectedState }
>set  { protectedState = newValue }
> }
>}
> }
> 
>> 
>> -- 
>> Brent Royal-Gordon
>> Architechies
>> 
>> ___
>> swift-evolution mailing list
>> swift-evolution@swift.org
>> https://lists.swift.org/mailman/listinfo/swift-evolution
> 

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Matthew Johnson via swift-evolution

> On Feb 21, 2017, at 9:47 PM, Brent Royal-Gordon via swift-evolution 
>  wrote:
> 
>> On Feb 21, 2017, at 7:38 PM, Robert Widmann  wrote:
>> 
>> Correct.  Because, in dividing the submodule across an extension, you have 
>> placed what should be a private API into a differently-scoped location.
> 
> Okay. So is your submodule design not intended to address the "I want to 
> encapsulate implementation details so they're only visible to several units 
> of code in different files, but not the entire module" use case? Because if 
> there's no way to scope a symbol to "everything inside this submodule, but 
> nothing outside this submodule", I think it leaves that use case unserved.

Unless I’m missing something there is also another encapsulation-related 
problem with the proposed design.  Let’s suppose for the sake of discussion 
there was a `submoduleprivate` access modifier (intentionally ungainly and not 
realistic).

// File 1
module Foo {
// internal, visible to the whole module
class Bar { submoduleprivate var protectedState: Int = 0 }
}

// File 2 - Has nothing to do with Foo at all
import MyModule.Foo

module NotFoo {
   // Hey, I need to see Bar.protectedState!!!
   func totallyNotFoo() {
   var bar = Bar()
   bar.foosExposedPrivates = 42
   }
}

// ok, I’ll just add an extension to Foo so I can see submoduleprivate and wrap 
what I need
module Foo {
// Hey, I’ll be nice and keep it fileprivate, but I could make it public if 
I wanted to.
extension Bar {
 fileprivate var foosExposedPrivates: Int {
// Yep, I’m inside Foo so I can see it’s submoduleprivate stuff
get { return protectedState }
set  { protectedState = newValue }
 }
}
}

> 
> -- 
> Brent Royal-Gordon
> Architechies
> 
> ___
> swift-evolution mailing list
> swift-evolution@swift.org
> https://lists.swift.org/mailman/listinfo/swift-evolution

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Daniel Duan via swift-evolution
FWIW, I like the freedom of choice. A Java-like file-based solution can be 
limiting for *some* style of programming. It is, as Robert mentioned, geared 
towards benefit of the implementation. I also suspect ppl who are asking for 
file-based solution _now_ may find themselves wanting the alternative in the 
future. Point is, let’s support both and let ppl use a linter.

> On Feb 21, 2017, at 7:46 PM, Xiaodi Wu via swift-evolution 
>  wrote:
> 
> Well put. As for me, it is not the syntactic delta with which I am concerned. 
> It is just a canary for the organizational delta.
> 
> There are certain freedoms enabled not by the _lack_ of constraints but 
> rather their judicious application. Swift has in the past--and it is your 
> burden to justify why it shouldn't continue to in the future--judged the 
> file-based approach to be one such judicious constraint.
> 
> 
> On Tue, Feb 21, 2017 at 21:42 Robert Widmann  > wrote:
>> On Feb 21, 2017, at 10:36 PM, Matthew Johnson > > wrote:
>> 
>>> 
>>> On Feb 21, 2017, at 9:28 PM, Robert Widmann via swift-evolution 
>>> > wrote:
>>> 
 
 On Feb 21, 2017, at 10:03 PM, Xiaodi Wu > wrote:
 
 On Tue, Feb 21, 2017 at 8:41 PM, Robert Widmann >wrote:
 
> On Feb 21, 2017, at 9:37 PM, Xiaodi Wu  > wrote:
> 
> On Tue, Feb 21, 2017 at 8:22 PM, Robert Widmann  >wrote:
> 
>> On Feb 21, 2017, at 9:13 PM, Xiaodi Wu > > wrote:
>> 
>> On Tue, Feb 21, 2017 at 7:59 PM, Robert Widmann via swift-evolution 
>> > wrote:
>> 
>>> On Feb 21, 2017, at 7:36 PM, Nevin Brackett-Rozinsky via 
>>> swift-evolution >> > wrote:
>>> 
>>> To my mind, any submodule system for Swift should be designed to 
>>> relieve the pressure for long files, and make it easy to group tightly 
>>> related files into a single unit with shared visibility. That way 
>>> developers can easily organize their code into smaller files while 
>>> utilizing Swift’s pattern of providing protocol conformances in 
>>> extensions and keeping implementation details hidden from the rest of 
>>> the module at large.
>>> 
>> 
>> Wonderful, because that’s absolutely supported by this proposal.  To 
>> group tightly related files into a single unit, simply declare a 
>> submodule for them and extend it in each of your related files.
>> 
>> It's supported, but it isn't first-class. By this I mean: there are two 
>> distinguishable uses supported by your proposal, lumped together by the 
>> fact that they are both about grouping units of code together. Put 
>> crudely, one use case is grouping lines of code, while the other is 
>> about grouping files of code. The merits of supporting both have already 
>> been debated in this discussion. The issue I'll touch on is supporting 
>> both with the same syntax. The chief drawbacks here are:
>> 
> 
> What exactly would be required to make it first class?  Referencing file 
> names in the module declaration?
> 
>  See below.
>> - It makes sense to use braces to group lines of code, but it makes no 
>> sense to use braces to group files of code; this just causes entire 
>> files to be indented.
>> 
> 
> If braces aren’t used to demarcate scopes, nesting modules becomes 
> ambiguous.
> 
> Again, let's observe the distinction about grouping files vs. grouping 
> lines.
> 
> Grouping files does not require braces: if the intended use of your 
> feature were to label files X, Y, and Z as belonging to one submodule and 
> A, B, and C to another, it would not matter if X, Y, and Z belonged to 
> Foo.Bar and A, B, and C to Foo.Bar.Baz: your syntax would not require 
> braces.
>  
> It’s important to note that indentation is one particular style.  LLVM 
> code style, in particular, chooses not to indent after namespace 
> declarations.  This issue also crops up when dealing with nested type 
> declarations, and I distinctly remember it not being a big enough deal to 
> "fix this" at the time when a proposal to “flatten” these declaration was 
> brought up.
>  
> Mine is not a critique of the syntax itself; I don't particularly care 
> about indents, nor do I mind not indenting namespaces.
> 
> What I'm saying 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Robert Widmann via swift-evolution
Whoops, move bar() out of the utility and you get the actual answer here, 
because you want to be able to see this in foo()!

> On Feb 21, 2017, at 10:54 PM, Robert Widmann  wrote:
> 
> This case is unserved because it is anti-modular and a nightmare to maintain. 
>  The actual way to structure this is to factor bar() and baz() into their own 
> utility submodule, or even deeper if necessary, that has as a parent the 
> primary module that wishes to consume them both but not re-export them out to 
> the parent.  For example,
> 
> 
>   // foo.swift
>   import MyMod.Submodule
>   func foo() {
>   bar()
>   }
> 
>   // bar.swift
> 
>// Make my utilities visible in Foo.Submodule, but invisible to the 
> parent.
>import Foo.Submodule.UtilitySubmodule
> 
>   module Submodule {
>   module UtilitySubmodule  {
>   internal func bar() {
>   baz()
> }
>   }
>   }
> 
>   // baz.swift
>   extension Submodule.UtilitySubmodule {  
>   internal func baz() {
>   …
>   }
>   }
> 
> The thought is that it should be as cheap to create submodules to organize 
> interfaces under as it is to create new directories to organize code under.
> 
> Though, this example is a little odd given that you’re defining and importing 
> the same utility submodule.  Really, what you would want to do is declare the 
> utility in its own file/files outside of bar.swift to really take full 
> advantage of the separation afforded here, then consume it internally with 
> the import as written here.
> 
>> On Feb 21, 2017, at 10:47 PM, Brent Royal-Gordon  
>> wrote:
>> 
>>> On Feb 21, 2017, at 7:38 PM, Robert Widmann  
>>> wrote:
>>> 
>>> Correct.  Because, in dividing the submodule across an extension, you have 
>>> placed what should be a private API into a differently-scoped location.
>> 
>> Okay. So is your submodule design not intended to address the "I want to 
>> encapsulate implementation details so they're only visible to several units 
>> of code in different files, but not the entire module" use case? Because if 
>> there's no way to scope a symbol to "everything inside this submodule, but 
>> nothing outside this submodule", I think it leaves that use case unserved.
>> 
>> -- 
>> Brent Royal-Gordon
>> Architechies
>> 
> 

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Robert Widmann via swift-evolution
This case is unserved because it is anti-modular and a nightmare to maintain.  
The actual way to structure this is to factor bar() and baz() into their own 
utility submodule, or even deeper if necessary, that has as a parent the 
primary module that wishes to consume them both but not re-export them out to 
the parent.  For example,


// foo.swift
import MyMod.Submodule
func foo() {
bar()
}

// bar.swift

// Make my utilities visible in Foo.Submodule, but invisible to the 
parent.
import Foo.Submodule.UtilitySubmodule

module Submodule {
module UtilitySubmodule  {
   internal func bar() {
baz()
  }
   }
}

// baz.swift
extension Submodule.UtilitySubmodule {  
internal func baz() {
…
}
}

The thought is that it should be as cheap to create submodules to organize 
interfaces under as it is to create new directories to organize code under.

Though, this example is a little odd given that you’re defining and importing 
the same utility submodule.  Really, what you would want to do is declare the 
utility in its own file/files outside of bar.swift to really take full 
advantage of the separation afforded here, then consume it internally with the 
import as written here.

> On Feb 21, 2017, at 10:47 PM, Brent Royal-Gordon  
> wrote:
> 
>> On Feb 21, 2017, at 7:38 PM, Robert Widmann  wrote:
>> 
>> Correct.  Because, in dividing the submodule across an extension, you have 
>> placed what should be a private API into a differently-scoped location.
> 
> Okay. So is your submodule design not intended to address the "I want to 
> encapsulate implementation details so they're only visible to several units 
> of code in different files, but not the entire module" use case? Because if 
> there's no way to scope a symbol to "everything inside this submodule, but 
> nothing outside this submodule", I think it leaves that use case unserved.
> 
> -- 
> Brent Royal-Gordon
> Architechies
> 

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Matthew Johnson via swift-evolution

> On Feb 21, 2017, at 9:42 PM, Robert Widmann  wrote:
> 
> 
>> On Feb 21, 2017, at 10:36 PM, Matthew Johnson > > wrote:
>> 
>>> 
>>> On Feb 21, 2017, at 9:28 PM, Robert Widmann via swift-evolution 
>>> > wrote:
>>> 
 
 On Feb 21, 2017, at 10:03 PM, Xiaodi Wu > wrote:
 
 On Tue, Feb 21, 2017 at 8:41 PM, Robert Widmann >wrote:
 
> On Feb 21, 2017, at 9:37 PM, Xiaodi Wu  > wrote:
> 
> On Tue, Feb 21, 2017 at 8:22 PM, Robert Widmann  >wrote:
> 
>> On Feb 21, 2017, at 9:13 PM, Xiaodi Wu > > wrote:
>> 
>> On Tue, Feb 21, 2017 at 7:59 PM, Robert Widmann via swift-evolution 
>> > wrote:
>> 
>>> On Feb 21, 2017, at 7:36 PM, Nevin Brackett-Rozinsky via 
>>> swift-evolution >> > wrote:
>>> 
>>> To my mind, any submodule system for Swift should be designed to 
>>> relieve the pressure for long files, and make it easy to group tightly 
>>> related files into a single unit with shared visibility. That way 
>>> developers can easily organize their code into smaller files while 
>>> utilizing Swift’s pattern of providing protocol conformances in 
>>> extensions and keeping implementation details hidden from the rest of 
>>> the module at large.
>>> 
>> 
>> Wonderful, because that’s absolutely supported by this proposal.  To 
>> group tightly related files into a single unit, simply declare a 
>> submodule for them and extend it in each of your related files.
>> 
>> It's supported, but it isn't first-class. By this I mean: there are two 
>> distinguishable uses supported by your proposal, lumped together by the 
>> fact that they are both about grouping units of code together. Put 
>> crudely, one use case is grouping lines of code, while the other is 
>> about grouping files of code. The merits of supporting both have already 
>> been debated in this discussion. The issue I'll touch on is supporting 
>> both with the same syntax. The chief drawbacks here are:
>> 
> 
> What exactly would be required to make it first class?  Referencing file 
> names in the module declaration?
> 
>  See below.
>> - It makes sense to use braces to group lines of code, but it makes no 
>> sense to use braces to group files of code; this just causes entire 
>> files to be indented.
>> 
> 
> If braces aren’t used to demarcate scopes, nesting modules becomes 
> ambiguous.
> 
> Again, let's observe the distinction about grouping files vs. grouping 
> lines.
> 
> Grouping files does not require braces: if the intended use of your 
> feature were to label files X, Y, and Z as belonging to one submodule and 
> A, B, and C to another, it would not matter if X, Y, and Z belonged to 
> Foo.Bar and A, B, and C to Foo.Bar.Baz: your syntax would not require 
> braces.
>  
> It’s important to note that indentation is one particular style.  LLVM 
> code style, in particular, chooses not to indent after namespace 
> declarations.  This issue also crops up when dealing with nested type 
> declarations, and I distinctly remember it not being a big enough deal to 
> "fix this" at the time when a proposal to “flatten” these declaration was 
> brought up.
>  
> Mine is not a critique of the syntax itself; I don't particularly care 
> about indents, nor do I mind not indenting namespaces.
> 
> What I'm saying is, you would not have chosen to require braces if your 
> proposed feature were aimed at making the grouping of files into 
> submodules as simple as possible. You chose to accommodate grouping lines 
> using the same syntax as grouping files over the simplest design for 
> grouping files. Make no mistake, this promotes one use over another.
 
 Ah, I see.  Yes, one of the stated goals is to become 
 filesystem-independent.  We certainly cannot do that by encouraging the 
 alternative.
  
 Swift's current design is deliberately not file system-independent. A 
 submodule design built on top of Swift could preserve that. Your draft 
 proposal makes two changes: it introduces a design for submodules; and, it 
 eliminates files as a unit of code by default (not least by declaring 
 `fileprivate` redundant). To my mind, you have presented no justification 
 for the 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Brent Royal-Gordon via swift-evolution
> On Feb 21, 2017, at 7:38 PM, Robert Widmann  wrote:
> 
> Correct.  Because, in dividing the submodule across an extension, you have 
> placed what should be a private API into a differently-scoped location.

Okay. So is your submodule design not intended to address the "I want to 
encapsulate implementation details so they're only visible to several units of 
code in different files, but not the entire module" use case? Because if 
there's no way to scope a symbol to "everything inside this submodule, but 
nothing outside this submodule", I think it leaves that use case unserved.

-- 
Brent Royal-Gordon
Architechies

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Xiaodi Wu via swift-evolution
Well put. As for me, it is not the syntactic delta with which I am
concerned. It is just a canary for the organizational delta.

There are certain freedoms enabled not by the _lack_ of constraints but
rather their judicious application. Swift has in the past--and it is your
burden to justify why it shouldn't continue to in the future--judged the
file-based approach to be one such judicious constraint.


On Tue, Feb 21, 2017 at 21:42 Robert Widmann 
wrote:

> On Feb 21, 2017, at 10:36 PM, Matthew Johnson 
> wrote:
>
>
> On Feb 21, 2017, at 9:28 PM, Robert Widmann via swift-evolution <
> swift-evolution@swift.org> wrote:
>
>
> On Feb 21, 2017, at 10:03 PM, Xiaodi Wu  wrote:
>
> On Tue, Feb 21, 2017 at 8:41 PM, Robert Widmann 
> wrote:
>
>
> On Feb 21, 2017, at 9:37 PM, Xiaodi Wu  wrote:
>
> On Tue, Feb 21, 2017 at 8:22 PM, Robert Widmann 
> wrote:
>
>
> On Feb 21, 2017, at 9:13 PM, Xiaodi Wu  wrote:
>
> On Tue, Feb 21, 2017 at 7:59 PM, Robert Widmann via swift-evolution <
> swift-evolution@swift.org> wrote:
>
>
> On Feb 21, 2017, at 7:36 PM, Nevin Brackett-Rozinsky via swift-evolution <
> swift-evolution@swift.org> wrote:
>
> To my mind, any submodule system for Swift should be designed to relieve
> the pressure for long files, and make it easy to group tightly related
> files into a single unit with shared visibility. That way developers can
> easily organize their code into smaller files while utilizing Swift’s
> pattern of providing protocol conformances in extensions and keeping
> implementation details hidden from the rest of the module at large.
>
>
> Wonderful, because that’s absolutely supported by this proposal.  To group
> tightly related files into a single unit, simply declare a submodule for
> them and extend it in each of your related files.
>
>
> It's supported, but it isn't first-class. By this I mean: there are two
> distinguishable uses supported by your proposal, lumped together by the
> fact that they are both about grouping units of code together. Put crudely,
> one use case is grouping lines of code, while the other is about grouping
> files of code. The merits of supporting both have already been debated in
> this discussion. The issue I'll touch on is supporting both with the same
> syntax. The chief drawbacks here are:
>
>
> What exactly would be required to *make* it first class?  Referencing
> file names in the module declaration?
>
>
>  See below.
>
> - It makes sense to use braces to group lines of code, but it makes no
> sense to use braces to group files of code; this just causes entire files
> to be indented.
>
>
> If braces aren’t used to demarcate scopes, nesting modules becomes
> ambiguous.
>
>
> Again, let's observe the distinction about grouping files vs. grouping
> lines.
>
> Grouping files does not require braces: if the intended use of your
> feature were to label files X, Y, and Z as belonging to one submodule and
> A, B, and C to another, it would not matter if X, Y, and Z belonged to
> Foo.Bar and A, B, and C to Foo.Bar.Baz: your syntax would not require
> braces.
>
>
> It’s important to note that indentation is one particular style.  LLVM
> code style, in particular, chooses not to indent after namespace
> declarations.  This issue also crops up when dealing with nested type
> declarations, and I distinctly remember it not being a big enough deal to
> "fix this" at the time when a proposal to “flatten” these declaration was
> brought up.
>
>
> Mine is not a critique of the syntax itself; I don't particularly care
> about indents, nor do I mind not indenting namespaces.
>
> What I'm saying is, you would not have chosen to require braces if your
> proposed feature were aimed at making the grouping of files into submodules
> as simple as possible. You chose to accommodate grouping lines using the
> same syntax as grouping files over the simplest design for grouping files.
> Make no mistake, this promotes one use over another.
>
>
> Ah, I see.  Yes, one of the stated goals is to become
> filesystem-independent.  We certainly cannot do that by encouraging the
> alternative.
>
>
> Swift's current design is deliberately not file system-independent. A
> submodule design built on top of Swift could preserve that. Your draft
> proposal makes two changes: it introduces a design for submodules; and, it
> eliminates files as a unit of code by default (not least by declaring
> `fileprivate` redundant). To my mind, you have presented no justification
> for the second change other than to say that it is a stated goal--but why?
>
>
>
>
>
>- fileprivate access can be recreated by creating a private "utility
>submodule" containing declarations of at most internal access.
>
>
>
>
> - Because some lines of code necessarily precede some other lines of code,
> it makes sense to declare the first group using `module` 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Robert Widmann via swift-evolution

> On Feb 21, 2017, at 10:36 PM, Matthew Johnson  wrote:
> 
>> 
>> On Feb 21, 2017, at 9:28 PM, Robert Widmann via swift-evolution 
>> > wrote:
>> 
>>> 
>>> On Feb 21, 2017, at 10:03 PM, Xiaodi Wu >> > wrote:
>>> 
>>> On Tue, Feb 21, 2017 at 8:41 PM, Robert Widmann >> >wrote:
>>> 
 On Feb 21, 2017, at 9:37 PM, Xiaodi Wu > wrote:
 
 On Tue, Feb 21, 2017 at 8:22 PM, Robert Widmann >wrote:
 
> On Feb 21, 2017, at 9:13 PM, Xiaodi Wu  > wrote:
> 
> On Tue, Feb 21, 2017 at 7:59 PM, Robert Widmann via swift-evolution 
> > wrote:
> 
>> On Feb 21, 2017, at 7:36 PM, Nevin Brackett-Rozinsky via swift-evolution 
>> > wrote:
>> 
>> To my mind, any submodule system for Swift should be designed to relieve 
>> the pressure for long files, and make it easy to group tightly related 
>> files into a single unit with shared visibility. That way developers can 
>> easily organize their code into smaller files while utilizing Swift’s 
>> pattern of providing protocol conformances in extensions and keeping 
>> implementation details hidden from the rest of the module at large.
>> 
> 
> Wonderful, because that’s absolutely supported by this proposal.  To 
> group tightly related files into a single unit, simply declare a 
> submodule for them and extend it in each of your related files.
> 
> It's supported, but it isn't first-class. By this I mean: there are two 
> distinguishable uses supported by your proposal, lumped together by the 
> fact that they are both about grouping units of code together. Put 
> crudely, one use case is grouping lines of code, while the other is about 
> grouping files of code. The merits of supporting both have already been 
> debated in this discussion. The issue I'll touch on is supporting both 
> with the same syntax. The chief drawbacks here are:
> 
 
 What exactly would be required to make it first class?  Referencing file 
 names in the module declaration?
 
  See below.
> - It makes sense to use braces to group lines of code, but it makes no 
> sense to use braces to group files of code; this just causes entire files 
> to be indented.
> 
 
 If braces aren’t used to demarcate scopes, nesting modules becomes 
 ambiguous.
 
 Again, let's observe the distinction about grouping files vs. grouping 
 lines.
 
 Grouping files does not require braces: if the intended use of your 
 feature were to label files X, Y, and Z as belonging to one submodule and 
 A, B, and C to another, it would not matter if X, Y, and Z belonged to 
 Foo.Bar and A, B, and C to Foo.Bar.Baz: your syntax would not require 
 braces.
  
 It’s important to note that indentation is one particular style.  LLVM 
 code style, in particular, chooses not to indent after namespace 
 declarations.  This issue also crops up when dealing with nested type 
 declarations, and I distinctly remember it not being a big enough deal to 
 "fix this" at the time when a proposal to “flatten” these declaration was 
 brought up.
  
 Mine is not a critique of the syntax itself; I don't particularly care 
 about indents, nor do I mind not indenting namespaces.
 
 What I'm saying is, you would not have chosen to require braces if your 
 proposed feature were aimed at making the grouping of files into 
 submodules as simple as possible. You chose to accommodate grouping lines 
 using the same syntax as grouping files over the simplest design for 
 grouping files. Make no mistake, this promotes one use over another.
>>> 
>>> Ah, I see.  Yes, one of the stated goals is to become 
>>> filesystem-independent.  We certainly cannot do that by encouraging the 
>>> alternative.
>>>  
>>> Swift's current design is deliberately not file system-independent. A 
>>> submodule design built on top of Swift could preserve that. Your draft 
>>> proposal makes two changes: it introduces a design for submodules; and, it 
>>> eliminates files as a unit of code by default (not least by declaring 
>>> `fileprivate` redundant). To my mind, you have presented no justification 
>>> for the second change other than to say that it is a stated goal--but why?
>> 
>> 
>> 
>> fileprivate access can be recreated by creating a private "utility 
>> submodule" containing declarations of at most internal access.
>> 
>> 
 
> - 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Xiaodi Wu via swift-evolution
On Tue, Feb 21, 2017 at 9:34 PM, Robert Widmann 
wrote:

> Let’s use some code to illustrate things.
>
> // FooUtilities.swift
> //
> // -module-name=Foo
> // module Foo {
> // Defines Foo.Utilities
> module Utilities {
>   internal func visibleInThisSubmodule() {}
> }
> //}
>
> // FooUtilities+MoreUtilities.swift
> extension Foo.Utilities {
>   private func privateHelper() {
> visibleInThisSubmodule()
>   }
> }
>

Either I'm entirely misunderstanding what you're trying to illustrate, or
this is totally unresponsive to Brent's question. In either case, I'll let
Brent ask his own question from here.


On Feb 21, 2017, at 10:31 PM, Xiaodi Wu  wrote:
>
> On Tue, Feb 21, 2017 at 9:29 PM, Robert Widmann 
> wrote:
>
>> Once again, internal is your keyword.  An extension allows you to “open
>> and expand” the module boundary here, which is exactly what you want here -
>> to extend this module across file boundaries without showing your cards to
>> an external consumer of your framework.
>>
>
> Sorry, I don't understand. Does your design support the use case below? I
> don't think it does. Are you replying that supporting the use case below is
> not a goal of your proposal? If so, please just say so.
>
>
> On Feb 21, 2017, at 10:26 PM, Xiaodi Wu  wrote:
>>
>> On Tue, Feb 21, 2017 at 9:08 PM, Robert Widmann via swift-evolution <
>> swift-evolution@swift.org> wrote:
>>
>>> Sorry, been replying to multiple sub-threads today.
>>>
>>>
>>> For bar(), because you wish to be able to
>>>
>>> 1) Not export it across the outermost module boundary
>>> 2) But still use it internally
>>>
>>> Internal access is required.  Any higher and you would export (violating
>>> 1), any lower and you wouldn’t be able to internally import (violating 2).
>>>
>>> For baz(), because you wish to be able to
>>>
>>> 1) Not export it across the outermost module boundary,
>>> 2) Or even your own internal submodule boundary
>>>
>>
>> 3) But still use it within the same submodule, across different file
>> boundaries: this is the feature that many people have stated they want to
>> emerge out of a submodule design.
>>
>> Private or fileprivate suffices depending on the scoping you wish for it
>>> to have within the file/interface it’s a part of relative to the other APIs
>>> in the submodule.
>>>
>>> > On Feb 21, 2017, at 10:04 PM, Brent Royal-Gordon <
>>> br...@architechies.com> wrote:
>>> >
>>> > I specified two different behaviors for `bar()` and `baz()`. I see now
>>> that you describe `internal` as having the behavior I want for `bar()`. Is
>>> there a way I can get the behavior I want for `baz()`?
>>> >
>>> > --
>>> > Brent Royal-Gordon
>>> > Sent from my iPhone
>>> >
>>> > On Feb 21, 2017, at 6:51 PM, Robert Widmann 
>>> wrote:
>>> >
>>> >>> What access modifiers do I put on `bar()` and `baz()` so that
>>> `MyMod` can access `bar()` but not `baz()`, and code outside `MyMod` can
>>> access neither `bar()` nor `baz()`?
>>> >>>
>>> >>
>>> >> internal
>>>
>>> ___
>>> swift-evolution mailing list
>>> swift-evolution@swift.org
>>> https://lists.swift.org/mailman/listinfo/swift-evolution
>>>
>>
>>
>
>
___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Robert Widmann via swift-evolution
Correct.  Because, in dividing the submodule across an extension, you have 
placed what should be a private API into a differently-scoped location.

> On Feb 21, 2017, at 10:34 PM, Brent Royal-Gordon  
> wrote:
> 
>> On Feb 21, 2017, at 7:14 PM, Robert Widmann  wrote:
>> 
>> Fileprivate and private are not changing at all.  Their meaning now extends 
>> from “private to this file” and “private to this declaration” respectively 
>> to those meanings plus “unexportable across any module boundary”.  One 
>> implication of this is it is now possible to create module-scoped private 
>> constants, functions, and data structures, which is one of the use-cases 
>> that Daniel Duan mentioned earlier down in the thread.
> 
> So what you are saying is that, in my example:
> 
>   // foo.swift
>   import MyMod.Submodule
>   func foo() {
>   bar()
>   }
> 
>   // bar.swift
>   module Submodule {
>   internal func bar() {
>   baz()
>   }
>   }
> 
>   // baz.swift
>   extension Submodule {   
>   ??? func baz() {
>   …
>   }
>   }
> 
> There is nothing I can put in the `???` slot that will expose `baz()` to 
> `bar()`, but not to `foo()`. Correct?
> 
> -- 
> Brent Royal-Gordon
> Architechies
> 

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Matthew Johnson via swift-evolution

> On Feb 21, 2017, at 9:28 PM, Robert Widmann via swift-evolution 
>  wrote:
> 
>> 
>> On Feb 21, 2017, at 10:03 PM, Xiaodi Wu > > wrote:
>> 
>> On Tue, Feb 21, 2017 at 8:41 PM, Robert Widmann > >wrote:
>> 
>>> On Feb 21, 2017, at 9:37 PM, Xiaodi Wu >> > wrote:
>>> 
>>> On Tue, Feb 21, 2017 at 8:22 PM, Robert Widmann >> >wrote:
>>> 
 On Feb 21, 2017, at 9:13 PM, Xiaodi Wu > wrote:
 
 On Tue, Feb 21, 2017 at 7:59 PM, Robert Widmann via swift-evolution 
 > wrote:
 
> On Feb 21, 2017, at 7:36 PM, Nevin Brackett-Rozinsky via swift-evolution 
> > wrote:
> 
> To my mind, any submodule system for Swift should be designed to relieve 
> the pressure for long files, and make it easy to group tightly related 
> files into a single unit with shared visibility. That way developers can 
> easily organize their code into smaller files while utilizing Swift’s 
> pattern of providing protocol conformances in extensions and keeping 
> implementation details hidden from the rest of the module at large.
> 
 
 Wonderful, because that’s absolutely supported by this proposal.  To group 
 tightly related files into a single unit, simply declare a submodule for 
 them and extend it in each of your related files.
 
 It's supported, but it isn't first-class. By this I mean: there are two 
 distinguishable uses supported by your proposal, lumped together by the 
 fact that they are both about grouping units of code together. Put 
 crudely, one use case is grouping lines of code, while the other is about 
 grouping files of code. The merits of supporting both have already been 
 debated in this discussion. The issue I'll touch on is supporting both 
 with the same syntax. The chief drawbacks here are:
 
>>> 
>>> What exactly would be required to make it first class?  Referencing file 
>>> names in the module declaration?
>>> 
>>>  See below.
 - It makes sense to use braces to group lines of code, but it makes no 
 sense to use braces to group files of code; this just causes entire files 
 to be indented.
 
>>> 
>>> If braces aren’t used to demarcate scopes, nesting modules becomes 
>>> ambiguous.
>>> 
>>> Again, let's observe the distinction about grouping files vs. grouping 
>>> lines.
>>> 
>>> Grouping files does not require braces: if the intended use of your feature 
>>> were to label files X, Y, and Z as belonging to one submodule and A, B, and 
>>> C to another, it would not matter if X, Y, and Z belonged to Foo.Bar and A, 
>>> B, and C to Foo.Bar.Baz: your syntax would not require braces.
>>>  
>>> It’s important to note that indentation is one particular style.  LLVM code 
>>> style, in particular, chooses not to indent after namespace declarations.  
>>> This issue also crops up when dealing with nested type declarations, and I 
>>> distinctly remember it not being a big enough deal to "fix this" at the 
>>> time when a proposal to “flatten” these declaration was brought up.
>>>  
>>> Mine is not a critique of the syntax itself; I don't particularly care 
>>> about indents, nor do I mind not indenting namespaces.
>>> 
>>> What I'm saying is, you would not have chosen to require braces if your 
>>> proposed feature were aimed at making the grouping of files into submodules 
>>> as simple as possible. You chose to accommodate grouping lines using the 
>>> same syntax as grouping files over the simplest design for grouping files. 
>>> Make no mistake, this promotes one use over another.
>> 
>> Ah, I see.  Yes, one of the stated goals is to become 
>> filesystem-independent.  We certainly cannot do that by encouraging the 
>> alternative.
>>  
>> Swift's current design is deliberately not file system-independent. A 
>> submodule design built on top of Swift could preserve that. Your draft 
>> proposal makes two changes: it introduces a design for submodules; and, it 
>> eliminates files as a unit of code by default (not least by declaring 
>> `fileprivate` redundant). To my mind, you have presented no justification 
>> for the second change other than to say that it is a stated goal--but why?
> 
> 
> 
> fileprivate access can be recreated by creating a private "utility submodule" 
> containing declarations of at most internal access.
> 
> 
>>> 
 - Because some lines of code necessarily precede some other lines of code, 
 it makes sense to declare the first group using `module` and to extend 
 that with the second group using `extension`. However, because a file of 
 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Xiaodi Wu via swift-evolution
On Tue, Feb 21, 2017 at 9:28 PM, Robert Widmann 
wrote:

>
> On Feb 21, 2017, at 10:03 PM, Xiaodi Wu  wrote:
>
> On Tue, Feb 21, 2017 at 8:41 PM, Robert Widmann 
> wrote:
>
>>
>> On Feb 21, 2017, at 9:37 PM, Xiaodi Wu  wrote:
>>
>> On Tue, Feb 21, 2017 at 8:22 PM, Robert Widmann > >wrote:
>>
>>>
>>> On Feb 21, 2017, at 9:13 PM, Xiaodi Wu  wrote:
>>>
>>> On Tue, Feb 21, 2017 at 7:59 PM, Robert Widmann via swift-evolution <
>>> swift-evolution@swift.org> wrote:
>>>

 On Feb 21, 2017, at 7:36 PM, Nevin Brackett-Rozinsky via
 swift-evolution  wrote:

 To my mind, any submodule system for Swift should be designed to
 relieve the pressure for long files, and make it easy to group tightly
 related files into a single unit with shared visibility. That way
 developers can easily organize their code into smaller files while
 utilizing Swift’s pattern of providing protocol conformances in extensions
 and keeping implementation details hidden from the rest of the module at
 large.


 Wonderful, because that’s absolutely supported by this proposal.  To
 group tightly related files into a single unit, simply declare a submodule
 for them and extend it in each of your related files.

>>>
>>> It's supported, but it isn't first-class. By this I mean: there are two
>>> distinguishable uses supported by your proposal, lumped together by the
>>> fact that they are both about grouping units of code together. Put crudely,
>>> one use case is grouping lines of code, while the other is about grouping
>>> files of code. The merits of supporting both have already been debated in
>>> this discussion. The issue I'll touch on is supporting both with the same
>>> syntax. The chief drawbacks here are:
>>>
>>>
>>> What exactly would be required to *make* it first class?  Referencing
>>> file names in the module declaration?
>>>
>>
>>  See below.
>>
>>> - It makes sense to use braces to group lines of code, but it makes no
>>> sense to use braces to group files of code; this just causes entire files
>>> to be indented.
>>>
>>>
>>> If braces aren’t used to demarcate scopes, nesting modules becomes
>>> ambiguous.
>>>
>>
>> Again, let's observe the distinction about grouping files vs. grouping
>> lines.
>>
>> Grouping files does not require braces: if the intended use of your
>> feature were to label files X, Y, and Z as belonging to one submodule and
>> A, B, and C to another, it would not matter if X, Y, and Z belonged to
>> Foo.Bar and A, B, and C to Foo.Bar.Baz: your syntax would not require
>> braces.
>>
>>
>>> It’s important to note that indentation is one particular style.  LLVM
>>> code style, in particular, chooses not to indent after namespace
>>> declarations.  This issue also crops up when dealing with nested type
>>> declarations, and I distinctly remember it not being a big enough deal to
>>> "fix this" at the time when a proposal to “flatten” these declaration was
>>> brought up.
>>>
>>
>> Mine is not a critique of the syntax itself; I don't particularly care
>> about indents, nor do I mind not indenting namespaces.
>>
>> What I'm saying is, you would not have chosen to require braces if your
>> proposed feature were aimed at making the grouping of files into submodules
>> as simple as possible. You chose to accommodate grouping lines using the
>> same syntax as grouping files over the simplest design for grouping files.
>> Make no mistake, this promotes one use over another.
>>
>>
>> Ah, I see.  Yes, one of the stated goals is to become
>> filesystem-independent.  We certainly cannot do that by encouraging the
>> alternative.
>>
>
> Swift's current design is deliberately not file system-independent. A
> submodule design built on top of Swift could preserve that. Your draft
> proposal makes two changes: it introduces a design for submodules; and, it
> eliminates files as a unit of code by default (not least by declaring
> `fileprivate` redundant). To my mind, you have presented no justification
> for the second change other than to say that it is a stated goal--but why?
>
>
>
>
>
>- fileprivate access can be recreated by creating a private "utility
>submodule" containing declarations of at most internal access.
>
>
>
>
>> - Because some lines of code necessarily precede some other lines of
>>> code, it makes sense to declare the first group using `module` and to
>>> extend that with the second group using `extension`. However, because a
>>> file of code does not necessarily precede another file of code, it is
>>> arbitrary which file is surrounded with a `module` declaration and which
>>> one is surrounded with an `extension` declaration.
>>>
>>>
>>> Absolutely.  But it is similarly arbitrary which public APIs are exposed
>>> in a type declaration and which are exposed in an extension 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Robert Widmann via swift-evolution
Let’s use some code to illustrate things.  

// FooUtilities.swift
//
// -module-name=Foo
// module Foo {
// Defines Foo.Utilities
module Utilities {
  internal func visibleInThisSubmodule() {}
}
//}

// FooUtilities+MoreUtilities.swift
extension Foo.Utilities {
  private func privateHelper() {
visibleInThisSubmodule()
  }
}



> On Feb 21, 2017, at 10:31 PM, Xiaodi Wu  wrote:
> 
> On Tue, Feb 21, 2017 at 9:29 PM, Robert Widmann  > wrote:
> Once again, internal is your keyword.  An extension allows you to “open and 
> expand” the module boundary here, which is exactly what you want here - to 
> extend this module across file boundaries without showing your cards to an 
> external consumer of your framework. 
> 
> Sorry, I don't understand. Does your design support the use case below? I 
> don't think it does. Are you replying that supporting the use case below is 
> not a goal of your proposal? If so, please just say so.
> 
> 
>> On Feb 21, 2017, at 10:26 PM, Xiaodi Wu > > wrote:
>> 
>> On Tue, Feb 21, 2017 at 9:08 PM, Robert Widmann via swift-evolution 
>> > wrote:
>> Sorry, been replying to multiple sub-threads today.
>> 
>> 
>> For bar(), because you wish to be able to
>> 
>> 1) Not export it across the outermost module boundary
>> 2) But still use it internally
>> 
>> Internal access is required.  Any higher and you would export (violating 1), 
>> any lower and you wouldn’t be able to internally import (violating 2).
>> 
>> For baz(), because you wish to be able to
>> 
>> 1) Not export it across the outermost module boundary,
>> 2) Or even your own internal submodule boundary
>>  
>> 3) But still use it within the same submodule, across different file 
>> boundaries: this is the feature that many people have stated they want to 
>> emerge out of a submodule design.
>> 
>> Private or fileprivate suffices depending on the scoping you wish for it to 
>> have within the file/interface it’s a part of relative to the other APIs in 
>> the submodule.
>> 
>> > On Feb 21, 2017, at 10:04 PM, Brent Royal-Gordon > > > wrote:
>> >
>> > I specified two different behaviors for `bar()` and `baz()`. I see now 
>> > that you describe `internal` as having the behavior I want for `bar()`. Is 
>> > there a way I can get the behavior I want for `baz()`?
>> >
>> > --
>> > Brent Royal-Gordon
>> > Sent from my iPhone
>> >
>> > On Feb 21, 2017, at 6:51 PM, Robert Widmann > > > wrote:
>> >
>> >>> What access modifiers do I put on `bar()` and `baz()` so that `MyMod` 
>> >>> can access `bar()` but not `baz()`, and code outside `MyMod` can access 
>> >>> neither `bar()` nor `baz()`?
>> >>>
>> >>
>> >> internal
>> 
>> ___
>> swift-evolution mailing list
>> swift-evolution@swift.org 
>> https://lists.swift.org/mailman/listinfo/swift-evolution 
>> 
> 

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Brent Royal-Gordon via swift-evolution
> On Feb 21, 2017, at 7:14 PM, Robert Widmann  wrote:
> 
> Fileprivate and private are not changing at all.  Their meaning now extends 
> from “private to this file” and “private to this declaration” respectively to 
> those meanings plus “unexportable across any module boundary”.  One 
> implication of this is it is now possible to create module-scoped private 
> constants, functions, and data structures, which is one of the use-cases that 
> Daniel Duan mentioned earlier down in the thread.

So what you are saying is that, in my example:

// foo.swift
import MyMod.Submodule
func foo() {
bar()
}

// bar.swift
module Submodule {
internal func bar() {
baz()
}
}

// baz.swift
extension Submodule {   
??? func baz() {
…
}
}

There is nothing I can put in the `???` slot that will expose `baz()` to 
`bar()`, but not to `foo()`. Correct?

-- 
Brent Royal-Gordon
Architechies

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Xiaodi Wu via swift-evolution
On Tue, Feb 21, 2017 at 9:29 PM, Robert Widmann 
wrote:

> Once again, internal is your keyword.  An extension allows you to “open
> and expand” the module boundary here, which is exactly what you want here -
> to extend this module across file boundaries without showing your cards to
> an external consumer of your framework.
>

Sorry, I don't understand. Does your design support the use case below? I
don't think it does. Are you replying that supporting the use case below is
not a goal of your proposal? If so, please just say so.


On Feb 21, 2017, at 10:26 PM, Xiaodi Wu  wrote:
>
> On Tue, Feb 21, 2017 at 9:08 PM, Robert Widmann via swift-evolution <
> swift-evolution@swift.org> wrote:
>
>> Sorry, been replying to multiple sub-threads today.
>>
>>
>> For bar(), because you wish to be able to
>>
>> 1) Not export it across the outermost module boundary
>> 2) But still use it internally
>>
>> Internal access is required.  Any higher and you would export (violating
>> 1), any lower and you wouldn’t be able to internally import (violating 2).
>>
>> For baz(), because you wish to be able to
>>
>> 1) Not export it across the outermost module boundary,
>> 2) Or even your own internal submodule boundary
>>
>
> 3) But still use it within the same submodule, across different file
> boundaries: this is the feature that many people have stated they want to
> emerge out of a submodule design.
>
> Private or fileprivate suffices depending on the scoping you wish for it
>> to have within the file/interface it’s a part of relative to the other APIs
>> in the submodule.
>>
>> > On Feb 21, 2017, at 10:04 PM, Brent Royal-Gordon <
>> br...@architechies.com> wrote:
>> >
>> > I specified two different behaviors for `bar()` and `baz()`. I see now
>> that you describe `internal` as having the behavior I want for `bar()`. Is
>> there a way I can get the behavior I want for `baz()`?
>> >
>> > --
>> > Brent Royal-Gordon
>> > Sent from my iPhone
>> >
>> > On Feb 21, 2017, at 6:51 PM, Robert Widmann 
>> wrote:
>> >
>> >>> What access modifiers do I put on `bar()` and `baz()` so that `MyMod`
>> can access `bar()` but not `baz()`, and code outside `MyMod` can access
>> neither `bar()` nor `baz()`?
>> >>>
>> >>
>> >> internal
>>
>> ___
>> swift-evolution mailing list
>> swift-evolution@swift.org
>> https://lists.swift.org/mailman/listinfo/swift-evolution
>>
>
>
___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Robert Widmann via swift-evolution
Once again, internal is your keyword.  An extension allows you to “open and 
expand” the module boundary here, which is exactly what you want here - to 
extend this module across file boundaries without showing your cards to an 
external consumer of your framework. 

> On Feb 21, 2017, at 10:26 PM, Xiaodi Wu  wrote:
> 
> On Tue, Feb 21, 2017 at 9:08 PM, Robert Widmann via swift-evolution 
> > wrote:
> Sorry, been replying to multiple sub-threads today.
> 
> 
> For bar(), because you wish to be able to
> 
> 1) Not export it across the outermost module boundary
> 2) But still use it internally
> 
> Internal access is required.  Any higher and you would export (violating 1), 
> any lower and you wouldn’t be able to internally import (violating 2).
> 
> For baz(), because you wish to be able to
> 
> 1) Not export it across the outermost module boundary,
> 2) Or even your own internal submodule boundary
>  
> 3) But still use it within the same submodule, across different file 
> boundaries: this is the feature that many people have stated they want to 
> emerge out of a submodule design.
> 
> Private or fileprivate suffices depending on the scoping you wish for it to 
> have within the file/interface it’s a part of relative to the other APIs in 
> the submodule.
> 
> > On Feb 21, 2017, at 10:04 PM, Brent Royal-Gordon  > > wrote:
> >
> > I specified two different behaviors for `bar()` and `baz()`. I see now that 
> > you describe `internal` as having the behavior I want for `bar()`. Is there 
> > a way I can get the behavior I want for `baz()`?
> >
> > --
> > Brent Royal-Gordon
> > Sent from my iPhone
> >
> > On Feb 21, 2017, at 6:51 PM, Robert Widmann  > > wrote:
> >
> >>> What access modifiers do I put on `bar()` and `baz()` so that `MyMod` can 
> >>> access `bar()` but not `baz()`, and code outside `MyMod` can access 
> >>> neither `bar()` nor `baz()`?
> >>>
> >>
> >> internal
> 
> ___
> swift-evolution mailing list
> swift-evolution@swift.org 
> https://lists.swift.org/mailman/listinfo/swift-evolution 
> 
___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Robert Widmann via swift-evolution

> On Feb 21, 2017, at 10:03 PM, Xiaodi Wu  wrote:
> 
> On Tue, Feb 21, 2017 at 8:41 PM, Robert Widmann  >wrote:
> 
>> On Feb 21, 2017, at 9:37 PM, Xiaodi Wu > > wrote:
>> 
>> On Tue, Feb 21, 2017 at 8:22 PM, Robert Widmann > >wrote:
>> 
>>> On Feb 21, 2017, at 9:13 PM, Xiaodi Wu >> > wrote:
>>> 
>>> On Tue, Feb 21, 2017 at 7:59 PM, Robert Widmann via swift-evolution 
>>> > wrote:
>>> 
 On Feb 21, 2017, at 7:36 PM, Nevin Brackett-Rozinsky via swift-evolution 
 > wrote:
 
 To my mind, any submodule system for Swift should be designed to relieve 
 the pressure for long files, and make it easy to group tightly related 
 files into a single unit with shared visibility. That way developers can 
 easily organize their code into smaller files while utilizing Swift’s 
 pattern of providing protocol conformances in extensions and keeping 
 implementation details hidden from the rest of the module at large.
 
>>> 
>>> Wonderful, because that’s absolutely supported by this proposal.  To group 
>>> tightly related files into a single unit, simply declare a submodule for 
>>> them and extend it in each of your related files.
>>> 
>>> It's supported, but it isn't first-class. By this I mean: there are two 
>>> distinguishable uses supported by your proposal, lumped together by the 
>>> fact that they are both about grouping units of code together. Put crudely, 
>>> one use case is grouping lines of code, while the other is about grouping 
>>> files of code. The merits of supporting both have already been debated in 
>>> this discussion. The issue I'll touch on is supporting both with the same 
>>> syntax. The chief drawbacks here are:
>>> 
>> 
>> What exactly would be required to make it first class?  Referencing file 
>> names in the module declaration?
>> 
>>  See below.
>>> - It makes sense to use braces to group lines of code, but it makes no 
>>> sense to use braces to group files of code; this just causes entire files 
>>> to be indented.
>>> 
>> 
>> If braces aren’t used to demarcate scopes, nesting modules becomes ambiguous.
>> 
>> Again, let's observe the distinction about grouping files vs. grouping lines.
>> 
>> Grouping files does not require braces: if the intended use of your feature 
>> were to label files X, Y, and Z as belonging to one submodule and A, B, and 
>> C to another, it would not matter if X, Y, and Z belonged to Foo.Bar and A, 
>> B, and C to Foo.Bar.Baz: your syntax would not require braces.
>>  
>> It’s important to note that indentation is one particular style.  LLVM code 
>> style, in particular, chooses not to indent after namespace declarations.  
>> This issue also crops up when dealing with nested type declarations, and I 
>> distinctly remember it not being a big enough deal to "fix this" at the time 
>> when a proposal to “flatten” these declaration was brought up.
>>  
>> Mine is not a critique of the syntax itself; I don't particularly care about 
>> indents, nor do I mind not indenting namespaces.
>> 
>> What I'm saying is, you would not have chosen to require braces if your 
>> proposed feature were aimed at making the grouping of files into submodules 
>> as simple as possible. You chose to accommodate grouping lines using the 
>> same syntax as grouping files over the simplest design for grouping files. 
>> Make no mistake, this promotes one use over another.
> 
> Ah, I see.  Yes, one of the stated goals is to become filesystem-independent. 
>  We certainly cannot do that by encouraging the alternative.
>  
> Swift's current design is deliberately not file system-independent. A 
> submodule design built on top of Swift could preserve that. Your draft 
> proposal makes two changes: it introduces a design for submodules; and, it 
> eliminates files as a unit of code by default (not least by declaring 
> `fileprivate` redundant). To my mind, you have presented no justification for 
> the second change other than to say that it is a stated goal--but why?



fileprivate access can be recreated by creating a private "utility submodule" 
containing declarations of at most internal access.


>> 
>>> - Because some lines of code necessarily precede some other lines of code, 
>>> it makes sense to declare the first group using `module` and to extend that 
>>> with the second group using `extension`. However, because a file of code 
>>> does not necessarily precede another file of code, it is arbitrary which 
>>> file is surrounded with a `module` declaration and which one is surrounded 
>>> with an `extension` declaration.
>> 
>> Absolutely.  But it is similarly arbitrary which public 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Xiaodi Wu via swift-evolution
On Tue, Feb 21, 2017 at 9:08 PM, Robert Widmann via swift-evolution <
swift-evolution@swift.org> wrote:

> Sorry, been replying to multiple sub-threads today.
>
>
> For bar(), because you wish to be able to
>
> 1) Not export it across the outermost module boundary
> 2) But still use it internally
>
> Internal access is required.  Any higher and you would export (violating
> 1), any lower and you wouldn’t be able to internally import (violating 2).
>
> For baz(), because you wish to be able to
>
> 1) Not export it across the outermost module boundary,
> 2) Or even your own internal submodule boundary
>

3) But still use it within the same submodule, across different file
boundaries: this is the feature that many people have stated they want to
emerge out of a submodule design.

Private or fileprivate suffices depending on the scoping you wish for it to
> have within the file/interface it’s a part of relative to the other APIs in
> the submodule.
>
> > On Feb 21, 2017, at 10:04 PM, Brent Royal-Gordon 
> wrote:
> >
> > I specified two different behaviors for `bar()` and `baz()`. I see now
> that you describe `internal` as having the behavior I want for `bar()`. Is
> there a way I can get the behavior I want for `baz()`?
> >
> > --
> > Brent Royal-Gordon
> > Sent from my iPhone
> >
> > On Feb 21, 2017, at 6:51 PM, Robert Widmann 
> wrote:
> >
> >>> What access modifiers do I put on `bar()` and `baz()` so that `MyMod`
> can access `bar()` but not `baz()`, and code outside `MyMod` can access
> neither `bar()` nor `baz()`?
> >>>
> >>
> >> internal
>
> ___
> swift-evolution mailing list
> swift-evolution@swift.org
> https://lists.swift.org/mailman/listinfo/swift-evolution
>
___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Robert Widmann via swift-evolution
Fileprivate and private are not changing at all.  Their meaning now extends 
from “private to this file” and “private to this declaration” respectively to 
those meanings plus “unexportable across any module boundary”.  One implication 
of this is it is now possible to create module-scoped private constants, 
functions, and data structures, which is one of the use-cases that Daniel Duan 
mentioned earlier down in the thread.

> On Feb 21, 2017, at 10:12 PM, Brent Royal-Gordon  
> wrote:
> 
> So are private and/or fileprivate changing to mean "visible within current 
> submodule"? Because I specified that baz() is in a type extension, possibly 
> in another file. 
> 
> -- 
> Brent Royal-Gordon
> Sent from my iPhone
> 
>> On Feb 21, 2017, at 7:08 PM, Robert Widmann  wrote:
>> 
>> For baz(), because you wish to be able to
>> 
>> 1) Not export it across the outermost module boundary, 
>> 2) Or even your own internal submodule boundary
>> 
>> Private or fileprivate suffices depending on the scoping you wish for it to 
>> have within the file/interface it’s a part of relative to the other APIs in 
>> the submodule.

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Brent Royal-Gordon via swift-evolution
So are private and/or fileprivate changing to mean "visible within current 
submodule"? Because I specified that baz() is in a type extension, possibly in 
another file. 

-- 
Brent Royal-Gordon
Sent from my iPhone

> On Feb 21, 2017, at 7:08 PM, Robert Widmann  wrote:
> 
> For baz(), because you wish to be able to
> 
> 1) Not export it across the outermost module boundary, 
> 2) Or even your own internal submodule boundary
> 
> Private or fileprivate suffices depending on the scoping you wish for it to 
> have within the file/interface it’s a part of relative to the other APIs in 
> the submodule.
___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Robert Widmann via swift-evolution
Sorry, been replying to multiple sub-threads today.


For bar(), because you wish to be able to 

1) Not export it across the outermost module boundary
2) But still use it internally

Internal access is required.  Any higher and you would export (violating 1), 
any lower and you wouldn’t be able to internally import (violating 2).

For baz(), because you wish to be able to

1) Not export it across the outermost module boundary, 
2) Or even your own internal submodule boundary

Private or fileprivate suffices depending on the scoping you wish for it to 
have within the file/interface it’s a part of relative to the other APIs in the 
submodule.

> On Feb 21, 2017, at 10:04 PM, Brent Royal-Gordon  
> wrote:
> 
> I specified two different behaviors for `bar()` and `baz()`. I see now that 
> you describe `internal` as having the behavior I want for `bar()`. Is there a 
> way I can get the behavior I want for `baz()`?
> 
> -- 
> Brent Royal-Gordon
> Sent from my iPhone
> 
> On Feb 21, 2017, at 6:51 PM, Robert Widmann  wrote:
> 
>>> What access modifiers do I put on `bar()` and `baz()` so that `MyMod` can 
>>> access `bar()` but not `baz()`, and code outside `MyMod` can access neither 
>>> `bar()` nor `baz()`?
>>> 
>> 
>> internal

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Xiaodi Wu via swift-evolution
On Tue, Feb 21, 2017 at 8:51 PM, Robert Widmann via swift-evolution <
swift-evolution@swift.org> wrote:

>
> On Feb 21, 2017, at 9:49 PM, Brent Royal-Gordon 
> wrote:
>
> On Feb 21, 2017, at 6:43 PM, Robert Widmann 
> wrote:
>
> That is not what this proposal requires.  A public API is ripe for
> re(export), but if the parent wishes to communicate with its children
> without exporting across the module boundary, see the definition of
> `internal`.
>
>
> I'm not sure whether I'm misunderstanding or we're talking past each other.
>
> Let me state this really simply. You have some code in a top-level module,
> `MyMod`:
>
> import MyMod.Submodule
>
> func foo() {
> bar()
> }
>
> And you have some other code in a submodule:
>
> module Submodule {
> ??? func bar() {
> baz()
> }
> }
>
> And then—perhaps in a separate file—you have some other code in an
> extension of the submodule:
>
> extension Submodule {
> ??? func baz() {
> …
> }
> }
>
> What access modifiers do I put on `bar()` and `baz()` so that `MyMod` can
> access `bar()` but not `baz()`, and code outside `MyMod` can access neither
> `bar()` nor `baz()`?
>
>
> internal
>

Huh? Brent wants `bar()` to be visible inside `foo()`, but not `baz()`. How
can they both use `internal`?


>
>- open and public declarations are exported by a module for
>consumption by clients of the module.
>
>
>- internal declarations scope over the entire module and any derived
>submodules.
>
> This way you can consume your own interface without it crossing the module
> boundary.
>
> --
> Brent Royal-Gordon
> Architechies
>
>
>
> ___
> swift-evolution mailing list
> swift-evolution@swift.org
> https://lists.swift.org/mailman/listinfo/swift-evolution
>
>
___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Brent Royal-Gordon via swift-evolution
I specified two different behaviors for `bar()` and `baz()`. I see now that you 
describe `internal` as having the behavior I want for `bar()`. Is there a way I 
can get the behavior I want for `baz()`?

-- 
Brent Royal-Gordon
Sent from my iPhone

On Feb 21, 2017, at 6:51 PM, Robert Widmann  wrote:

>> What access modifiers do I put on `bar()` and `baz()` so that `MyMod` can 
>> access `bar()` but not `baz()`, and code outside `MyMod` can access neither 
>> `bar()` nor `baz()`?
>> 
> 
> internal
___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Xiaodi Wu via swift-evolution
On Tue, Feb 21, 2017 at 8:41 PM, Robert Widmann 
wrote:

>
> On Feb 21, 2017, at 9:37 PM, Xiaodi Wu  wrote:
>
> On Tue, Feb 21, 2017 at 8:22 PM, Robert Widmann 
> wrote:
>
>>
>> On Feb 21, 2017, at 9:13 PM, Xiaodi Wu  wrote:
>>
>> On Tue, Feb 21, 2017 at 7:59 PM, Robert Widmann via swift-evolution <
>> swift-evolution@swift.org> wrote:
>>
>>>
>>> On Feb 21, 2017, at 7:36 PM, Nevin Brackett-Rozinsky via swift-evolution
>>>  wrote:
>>>
>>> To my mind, any submodule system for Swift should be designed to relieve
>>> the pressure for long files, and make it easy to group tightly related
>>> files into a single unit with shared visibility. That way developers can
>>> easily organize their code into smaller files while utilizing Swift’s
>>> pattern of providing protocol conformances in extensions and keeping
>>> implementation details hidden from the rest of the module at large.
>>>
>>>
>>> Wonderful, because that’s absolutely supported by this proposal.  To
>>> group tightly related files into a single unit, simply declare a submodule
>>> for them and extend it in each of your related files.
>>>
>>
>> It's supported, but it isn't first-class. By this I mean: there are two
>> distinguishable uses supported by your proposal, lumped together by the
>> fact that they are both about grouping units of code together. Put crudely,
>> one use case is grouping lines of code, while the other is about grouping
>> files of code. The merits of supporting both have already been debated in
>> this discussion. The issue I'll touch on is supporting both with the same
>> syntax. The chief drawbacks here are:
>>
>>
>> What exactly would be required to *make* it first class?  Referencing
>> file names in the module declaration?
>>
>
>  See below.
>
>> - It makes sense to use braces to group lines of code, but it makes no
>> sense to use braces to group files of code; this just causes entire files
>> to be indented.
>>
>>
>> If braces aren’t used to demarcate scopes, nesting modules becomes
>> ambiguous.
>>
>
> Again, let's observe the distinction about grouping files vs. grouping
> lines.
>
> Grouping files does not require braces: if the intended use of your
> feature were to label files X, Y, and Z as belonging to one submodule and
> A, B, and C to another, it would not matter if X, Y, and Z belonged to
> Foo.Bar and A, B, and C to Foo.Bar.Baz: your syntax would not require
> braces.
>
>
>> It’s important to note that indentation is one particular style.  LLVM
>> code style, in particular, chooses not to indent after namespace
>> declarations.  This issue also crops up when dealing with nested type
>> declarations, and I distinctly remember it not being a big enough deal to
>> "fix this" at the time when a proposal to “flatten” these declaration was
>> brought up.
>>
>
> Mine is not a critique of the syntax itself; I don't particularly care
> about indents, nor do I mind not indenting namespaces.
>
> What I'm saying is, you would not have chosen to require braces if your
> proposed feature were aimed at making the grouping of files into submodules
> as simple as possible. You chose to accommodate grouping lines using the
> same syntax as grouping files over the simplest design for grouping files.
> Make no mistake, this promotes one use over another.
>
>
> Ah, I see.  Yes, one of the stated goals is to become
> filesystem-independent.  We certainly cannot do that by encouraging the
> alternative.
>

Swift's current design is deliberately not file system-independent. A
submodule design built on top of Swift could preserve that. Your draft
proposal makes two changes: it introduces a design for submodules; and, it
eliminates files as a unit of code by default (not least by declaring
`fileprivate` redundant). To my mind, you have presented no justification
for the second change other than to say that it is a stated goal--but why?

>
> - Because some lines of code necessarily precede some other lines of code,
>> it makes sense to declare the first group using `module` and to extend that
>> with the second group using `extension`. However, because a file of code
>> does not necessarily precede another file of code, it is arbitrary which
>> file is surrounded with a `module` declaration and which one is surrounded
>> with an `extension` declaration.
>>
>>
>> Absolutely.  But it is similarly arbitrary which public APIs are exposed
>> in a type declaration and which are exposed in an extension declaration.
>>
>
> Not entirely, no. Stored properties must be in the type declaration. Enum
> cases must be in the type declaration. Perhaps you regard these as
> temporary inconveniences of the current grammar; I see them as quite
> reasonable ways to give some consistency as to what's written where in a
> language where types can be retroactively extended. In a very real sense,
> you must read the type declaration before you 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Robert Widmann via swift-evolution
What is implied by the definition of `internal` in the proposal (which should, 
as this thread has shown, be stated explicitly) is that by “export” we mean 
“export to clients” across the outermost module-boundary.  Any API that is not 
public is, by definition, not able to cross this outermost boundary.  Internal 
API is allowed to cross internal boundaries if it is imported internally.  
Private and fileprivate API may not, as the name implies, cross file boundaries 
and so cannot be allowed to cross either boundary.

> On Feb 21, 2017, at 9:49 PM, Brent Royal-Gordon  
> wrote:
> 
>> On Feb 21, 2017, at 6:43 PM, Robert Widmann  wrote:
>> 
>> That is not what this proposal requires.  A public API is ripe for 
>> re(export), but if the parent wishes to communicate with its children 
>> without exporting across the module boundary, see the definition of 
>> `internal`.
> 
> I'm not sure whether I'm misunderstanding or we're talking past each other.
> 
> Let me state this really simply. You have some code in a top-level module, 
> `MyMod`:
> 
>   import MyMod.Submodule
>   
>   func foo() {
>   bar()
>   }
> 
> And you have some other code in a submodule:
> 
>   module Submodule {
>   ??? func bar() {
>   baz()
>   }
>   }
> 
> And then—perhaps in a separate file—you have some other code in an extension 
> of the submodule:
> 
>   extension Submodule {   
>   ??? func baz() {
>   …
>   }
>   }
> 
> What access modifiers do I put on `bar()` and `baz()` so that `MyMod` can 
> access `bar()` but not `baz()`, and code outside `MyMod` can access neither 
> `bar()` nor `baz()`?
> 
> -- 
> Brent Royal-Gordon
> Architechies
> 

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Robert Widmann via swift-evolution

> On Feb 21, 2017, at 9:49 PM, Brent Royal-Gordon  
> wrote:
> 
>> On Feb 21, 2017, at 6:43 PM, Robert Widmann  wrote:
>> 
>> That is not what this proposal requires.  A public API is ripe for 
>> re(export), but if the parent wishes to communicate with its children 
>> without exporting across the module boundary, see the definition of 
>> `internal`.
> 
> I'm not sure whether I'm misunderstanding or we're talking past each other.
> 
> Let me state this really simply. You have some code in a top-level module, 
> `MyMod`:
> 
>   import MyMod.Submodule
>   
>   func foo() {
>   bar()
>   }
> 
> And you have some other code in a submodule:
> 
>   module Submodule {
>   ??? func bar() {
>   baz()
>   }
>   }
> 
> And then—perhaps in a separate file—you have some other code in an extension 
> of the submodule:
> 
>   extension Submodule {   
>   ??? func baz() {
>   …
>   }
>   }
> 
> What access modifiers do I put on `bar()` and `baz()` so that `MyMod` can 
> access `bar()` but not `baz()`, and code outside `MyMod` can access neither 
> `bar()` nor `baz()`?
> 

internal


open and public declarations are exported by a module for consumption by 
clients of the module.
internal declarations scope over the entire module and any derived submodules.
This way you can consume your own interface without it crossing the module 
boundary.

> -- 
> Brent Royal-Gordon
> Architechies
> 

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Brent Royal-Gordon via swift-evolution
> On Feb 21, 2017, at 6:43 PM, Robert Widmann  wrote:
> 
> That is not what this proposal requires.  A public API is ripe for 
> re(export), but if the parent wishes to communicate with its children without 
> exporting across the module boundary, see the definition of `internal`.

I'm not sure whether I'm misunderstanding or we're talking past each other.

Let me state this really simply. You have some code in a top-level module, 
`MyMod`:

import MyMod.Submodule

func foo() {
bar()
}

And you have some other code in a submodule:

module Submodule {
??? func bar() {
baz()
}
}

And then—perhaps in a separate file—you have some other code in an extension of 
the submodule:

extension Submodule {   
??? func baz() {
…
}
}

What access modifiers do I put on `bar()` and `baz()` so that `MyMod` can 
access `bar()` but not `baz()`, and code outside `MyMod` can access neither 
`bar()` nor `baz()`?

-- 
Brent Royal-Gordon
Architechies

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Robert Widmann via swift-evolution

> On Feb 21, 2017, at 9:44 PM, Xiaodi Wu  wrote:
> 
> On Tue, Feb 21, 2017 at 8:32 PM, Robert Widmann  > wrote:
> There’s an important distinction between the ability to wall off, and this 
> particular instance of doing so.  By definition, a module allows for the 
> encapsulation and export of a subset of an API, the same way access modifiers 
> allow types to expose an interface.  If the sub-parts of that API must 
> interact, they must by definition share the same concerns and belong together 
> under the same submodule.  If their implementations require separation then 
> further subdivisions can be made with further submodules.  This is the design 
> practice encouraged, and put to good use, by every other language with 
> modules since the heyday of Modula, and breaking that contract by creating 
> unnecessary parent divisions to introduce headaches for yourself is just 
> another case of anti-modular use of a modular system.  There’s nothing we can 
> do to stop you from asking for this, but that also doesn’t excuse the poor 
> design choice here - especially when it can be rectified by reshuffling your 
> own dependency graph.
> 
> Indeed, I won't disagree with you wrt _modules_. I notice you titled this 
> thread "submodules" but propose a syntax that uses the word `module`. Left 
> unsaid, I'd imagine, is that you regard a submodule as a 
> module-within-a-module.
> 
> This is *not*, as I understand it, what most people on this list are asking 
> for wrt _submodules_. Instead, they are asking for a unit of code greater 
> than a file but less than a module. To parallel that new facility, they want 
> an access level greater than fileprivate but less than internal. This draft 
> proposal (in its failure to acknowledge this frequent ask) explicitly but 
> _silently_ rejects those motivations.

So they want to be able to aggregate interfaces and define their exportability, 
while also maintaining the ability to scope a declaration to a particular 
grouping.  This is, quite literally, the semantics we have defined - with 
modules enabling aggregation and `internal` stretching to become this “new” 
access control kind.

> 
>> On Feb 21, 2017, at 9:19 PM, Xiaodi Wu > > wrote:
>> 
>> On Tue, Feb 21, 2017 at 8:15 PM, Robert Widmann via swift-evolution 
>> > wrote:
>> 
>>> On Feb 21, 2017, at 7:46 AM, Brent Royal-Gordon via swift-evolution 
>>> > wrote:
>>> 
 On Feb 21, 2017, at 1:28 AM, Daniel Duan via swift-evolution 
 > wrote:
 
 It has been my hope that a lightweight module system will remove the need 
 for `private` *and* `fileprivate`.
>>> 
>>> I really doubt it will. `private`/`fileprivate` works because you can also 
>>> access `internal` at the same time.
>>> 
>>> What I mean by that is, think about code like this:
>>> 
>>> // Foo.swift
>>> public class Foo {
>>> public init() { … }
>>> 
>>> func doBar() -> Quux {
>>> return helper(in: randomRange())
>>> }
>>> 
>>> private func helper(in range: Range) -> Quux {
>>> …
>>> }
>>> }
>>> 
>>> // Bar.swift
>>> public class Bar {
>>> public static let shared = Bar()
>>> 
>>> func baz(with foo: Foo) {
>>> let quux = foo.doBar()
>>> process(quux)
>>> }
>>> 
>>> private func process(_ quux: Quux) {
>>> …
>>> }
>>> }
>>> 
>>> These classes have `public` APIs that are externally visible, `internal` 
>>> APIs for communicating with each other, and `private` APIs for 
>>> implementation details. Now try to reproduce the same design with 
>>> submodules and `public`/`internal` only:
>>> 
>>> public import MyMod.Foo
>>> public import MyMod.Bar
>>> 
>>> module Foo {
>>> public class Foo {
>>> public init() { … }
>>> 
>>> 
>>> ??? func doBar() -> Quux {
>>> return helper(in: randomRange())
>>> }
>>> 
>>> func helper(in range: Range) -> Quux {
>>> …
>>> }
>>> }
>>> }
>>> 
>>> // Bar.swift
>>> module Bar {
>>> public class Bar {
>>> public static let shared = Bar()
>>> 
>>> ??? func baz(with foo: Foo) {
>>> let quux = foo.doBar()
>>> process(quux)
>>> }
>>> 
>>> func process(_ quux: Quux) {
>>>  

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Xiaodi Wu via swift-evolution
On Tue, Feb 21, 2017 at 8:32 PM, Robert Widmann 
wrote:

> There’s an important distinction between the ability to wall off, and this
> particular instance of doing so.  By definition, a module allows for the
> encapsulation and export of a subset of an API, the same way access
> modifiers allow types to expose an interface.  If the sub-parts of that API
> must interact, they must by definition share the same concerns and belong
> together under the same submodule.  If their implementations require
> separation then further subdivisions can be made with further submodules.
> This is the design practice encouraged, and put to good use, by every other
> language with modules since the heyday of Modula, and breaking that
> contract by creating unnecessary parent divisions to introduce headaches
> for yourself is just another case of anti-modular use of a modular system.
> There’s nothing we can do to stop you from asking for this, but that also
> doesn’t excuse the poor design choice here - especially when it can be
> rectified by reshuffling your own dependency graph.
>

Indeed, I won't disagree with you wrt _modules_. I notice you titled this
thread "submodules" but propose a syntax that uses the word `module`. Left
unsaid, I'd imagine, is that you regard a submodule as a
module-within-a-module.

This is *not*, as I understand it, what most people on this list are asking
for wrt _submodules_. Instead, they are asking for a unit of code greater
than a file but less than a module. To parallel that new facility, they
want an access level greater than fileprivate but less than internal. This
draft proposal (in its failure to acknowledge this frequent ask) explicitly
but _silently_ rejects those motivations.

On Feb 21, 2017, at 9:19 PM, Xiaodi Wu  wrote:
>
> On Tue, Feb 21, 2017 at 8:15 PM, Robert Widmann via swift-evolution <
> swift-evolution@swift.org> wrote:
>
>>
>> On Feb 21, 2017, at 7:46 AM, Brent Royal-Gordon via swift-evolution <
>> swift-evolution@swift.org> wrote:
>>
>> On Feb 21, 2017, at 1:28 AM, Daniel Duan via swift-evolution <
>> swift-evolution@swift.org> wrote:
>>
>> It has been my hope that a lightweight module system will remove the need
>> for `private` *and* `fileprivate`.
>>
>>
>> I really doubt it will. `private`/`fileprivate` works because you can
>> also access `internal` at the same time.
>>
>> What I mean by that is, think about code like this:
>>
>> // Foo.swift
>> public class Foo {
>> public init() { … }
>>
>> func doBar() -> Quux {
>> return helper(in: randomRange())
>> }
>>
>> private func helper(in range: Range) -> Quux {
>> …
>> }
>> }
>>
>> // Bar.swift
>> public class Bar {
>> public static let shared = Bar()
>>
>> func baz(with foo: Foo) {
>> let quux = foo.doBar()
>> process(quux)
>> }
>>
>> private func process(_ quux: Quux) {
>> …
>> }
>> }
>>
>> These classes have `public` APIs that are externally visible, `internal`
>> APIs for communicating with each other, and `private` APIs for
>> implementation details. Now try to reproduce the same design with
>> submodules and `public`/`internal` only:
>>
>> public import MyMod.Foo
>> public import MyMod.Bar
>>
>> module Foo {
>> public class Foo {
>> public init() { … }
>>
>>
>> ??? func doBar() -> Quux {
>> return helper(in: randomRange())
>> }
>>
>> func helper(in range: Range) -> Quux {
>> …
>> }
>> }
>> }
>>
>> // Bar.swift
>> module Bar {
>> public class Bar {
>> public static let shared = Bar()
>>
>> ??? func baz(with foo: Foo) {
>> let quux = foo.doBar()
>> process(quux)
>> }
>>
>> func process(_ quux: Quux) {
>> …
>> }
>> }
>> }
>>
>> The `doBar()` and `baz()` methods have to be either exposed to third
>> parties or kept away from yourself. That's just not viable.
>>
>>
>> If they must communicate, they can be a part of the same (sub)module.
>> This makes filling in these annotations trivial.  Nobody actually uses
>> modules to wall off their own APIs from themselves like this, they use
>> submodules to encapsulate the internal parts and surface public APIs in the
>> parent.
>>
>
> I think you'll find a ton of people on this list who would want to use
> submodules precisely to wall off their own APIs from themselves. Witness
> the hundreds of messages about new syntax to do just that.
>
>
>>
>> module Bar {
>>
>> public class Foo {
>>
>> public init() { … }
>>
>>
>>
>> internal func doBar() -> Quux {
>>
>> return helper(in: randomRange())
>>
>> }
>>
>>
>> internal func helper(in range: Range) -> Quux {
>>
>> …
>>
>> }
>>
>> }
>>
>> }
>>
>>
>> // Bar.swift
>>
>> extension Bar {
>>
>> public class Bar {
>>
>> public static let shared = Bar()
>>
>>
>> internal func baz(with foo: Foo) {
>>
>> let quux = foo.doBar()
>>
>> process(quux)
>>
>> }
>>
>>
>> internal func process(_ quux: Quux) {
>>
>> …
>>
>> }
>>
>> }
>> }
>>
>> --
>> Brent Royal-Gordon
>> Architechies
>>
>> ___
>> swift-evolution mailing list
>> swift-evolution@swift.org

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Robert Widmann via swift-evolution

> On Feb 21, 2017, at 9:38 PM, Brent Royal-Gordon  
> wrote:
> 
>> On Feb 21, 2017, at 6:09 PM, Robert Widmann  wrote:
>> 
>>> If I'm reading this correctly, you're proposing that the `internal` APIs in 
>>> a submodule should *not* be accessible to enclosing modules. I also don't 
>>> see any indication that you can control who is allowed to import a 
>>> particular submodule.
>>> 
>>> That means that, if you use a submodule to encapsulate internal state, the 
>>> APIs that are available to the parent module are *also* available to any 
>>> rando who feels like importing your submodule. I don't think that's going 
>>> to be a tenable design.
>> 
>> If the state is truly internal, and you are using internal access control, 
>> this is impossible.  The internal state cannot cross the module boundary 
>> unless it is marked public.  If a “random” feels like importing my 
>> submodule, they will not have access to any symbols.
> 
> I think you're missing my point.
> 
> What you appear to be saying is: "If two things need privileged access to 
> each other, they should be in the same module; if they should hide 
> implementation details from each other, they should be in different modules." 
> But it's perfectly possible for two things to *both* need privileged access 
> to some APIs *and* hide implementation details from one another.
> 
> Basically, my objection is, this proposal requires that parent modules only 
> communicate with submodules through fully `public` APIs which are also 
> available outside the module. If you want to encapsulate certain 
> implementation details by putting them in a submodule, you must paradoxically 
> expose other details—the APIs through which the parent module is supposed to 
> interact with the submodule—to the whole world. That restriction conflicts 
> with Swift's important goal of ensuring that libraries only expose API 
> surface they're committed to supporting indefinitely.

That is not what this proposal requires.  A public API is ripe for re(export), 
but if the parent wishes to communicate with its children without exporting 
across the module boundary, see the definition of `internal`.

> 
> Basically, I think that either we need a new access level meaning "visible to 
> the top-level module and all of its submodules, but not to other modules", or 
> we need a way to specify that a submodule is internal-only and shouldn't be 
> importable by outside code. My submodule sketch the other day took the second 
> approach, but I think one or the other is necessary if we want submodules to 
> serve both as public units of API surface and private encapsulators of 
> implementation detail.
> 
> -- 
> Brent Royal-Gordon
> Architechies
> 

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Robert Widmann via swift-evolution

> On Feb 21, 2017, at 9:37 PM, Xiaodi Wu  wrote:
> 
> On Tue, Feb 21, 2017 at 8:22 PM, Robert Widmann  >wrote:
> 
>> On Feb 21, 2017, at 9:13 PM, Xiaodi Wu > > wrote:
>> 
>> On Tue, Feb 21, 2017 at 7:59 PM, Robert Widmann via swift-evolution 
>> > wrote:
>> 
>>> On Feb 21, 2017, at 7:36 PM, Nevin Brackett-Rozinsky via swift-evolution 
>>> > wrote:
>>> 
>>> To my mind, any submodule system for Swift should be designed to relieve 
>>> the pressure for long files, and make it easy to group tightly related 
>>> files into a single unit with shared visibility. That way developers can 
>>> easily organize their code into smaller files while utilizing Swift’s 
>>> pattern of providing protocol conformances in extensions and keeping 
>>> implementation details hidden from the rest of the module at large.
>>> 
>> 
>> Wonderful, because that’s absolutely supported by this proposal.  To group 
>> tightly related files into a single unit, simply declare a submodule for 
>> them and extend it in each of your related files.
>> 
>> It's supported, but it isn't first-class. By this I mean: there are two 
>> distinguishable uses supported by your proposal, lumped together by the fact 
>> that they are both about grouping units of code together. Put crudely, one 
>> use case is grouping lines of code, while the other is about grouping files 
>> of code. The merits of supporting both have already been debated in this 
>> discussion. The issue I'll touch on is supporting both with the same syntax. 
>> The chief drawbacks here are:
>> 
> 
> What exactly would be required to make it first class?  Referencing file 
> names in the module declaration?
> 
>  See below.
>> - It makes sense to use braces to group lines of code, but it makes no sense 
>> to use braces to group files of code; this just causes entire files to be 
>> indented.
>> 
> 
> If braces aren’t used to demarcate scopes, nesting modules becomes ambiguous.
> 
> Again, let's observe the distinction about grouping files vs. grouping lines.
> 
> Grouping files does not require braces: if the intended use of your feature 
> were to label files X, Y, and Z as belonging to one submodule and A, B, and C 
> to another, it would not matter if X, Y, and Z belonged to Foo.Bar and A, B, 
> and C to Foo.Bar.Baz: your syntax would not require braces.
>  
> It’s important to note that indentation is one particular style.  LLVM code 
> style, in particular, chooses not to indent after namespace declarations.  
> This issue also crops up when dealing with nested type declarations, and I 
> distinctly remember it not being a big enough deal to "fix this" at the time 
> when a proposal to “flatten” these declaration was brought up.
>  
> Mine is not a critique of the syntax itself; I don't particularly care about 
> indents, nor do I mind not indenting namespaces.
> 
> What I'm saying is, you would not have chosen to require braces if your 
> proposed feature were aimed at making the grouping of files into submodules 
> as simple as possible. You chose to accommodate grouping lines using the same 
> syntax as grouping files over the simplest design for grouping files. Make no 
> mistake, this promotes one use over another.

Ah, I see.  Yes, one of the stated goals is to become filesystem-independent.  
We certainly cannot do that by encouraging the alternative.

> 
>> - Because some lines of code necessarily precede some other lines of code, 
>> it makes sense to declare the first group using `module` and to extend that 
>> with the second group using `extension`. However, because a file of code 
>> does not necessarily precede another file of code, it is arbitrary which 
>> file is surrounded with a `module` declaration and which one is surrounded 
>> with an `extension` declaration.
> 
> Absolutely.  But it is similarly arbitrary which public APIs are exposed in a 
> type declaration and which are exposed in an extension declaration.
> 
> Not entirely, no. Stored properties must be in the type declaration. Enum 
> cases must be in the type declaration. Perhaps you regard these as temporary 
> inconveniences of the current grammar; I see them as quite reasonable ways to 
> give some consistency as to what's written where in a language where types 
> can be retroactively extended. In a very real sense, you must read the type 
> declaration before you read the extensions in order to understand the latter. 
> By comparison, there is nothing that must be in your proposed module 
> declaration.
>  
> My hope is that the module declaration itself will become the one-stop-shop 
> for re-exports and general public bookkeeping just as aggregate declarations 
> are today.  Module extensions exist to accommodate users that wish to break 
> 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Brent Royal-Gordon via swift-evolution
> On Feb 21, 2017, at 6:09 PM, Robert Widmann  wrote:
> 
>> If I'm reading this correctly, you're proposing that the `internal` APIs in 
>> a submodule should *not* be accessible to enclosing modules. I also don't 
>> see any indication that you can control who is allowed to import a 
>> particular submodule.
>> 
>> That means that, if you use a submodule to encapsulate internal state, the 
>> APIs that are available to the parent module are *also* available to any 
>> rando who feels like importing your submodule. I don't think that's going to 
>> be a tenable design.
> 
> If the state is truly internal, and you are using internal access control, 
> this is impossible.  The internal state cannot cross the module boundary 
> unless it is marked public.  If a “random” feels like importing my submodule, 
> they will not have access to any symbols.

I think you're missing my point.

What you appear to be saying is: "If two things need privileged access to each 
other, they should be in the same module; if they should hide implementation 
details from each other, they should be in different modules." But it's 
perfectly possible for two things to *both* need privileged access to some APIs 
*and* hide implementation details from one another.

Basically, my objection is, this proposal requires that parent modules only 
communicate with submodules through fully `public` APIs which are also 
available outside the module. If you want to encapsulate certain implementation 
details by putting them in a submodule, you must paradoxically expose other 
details—the APIs through which the parent module is supposed to interact with 
the submodule—to the whole world. That restriction conflicts with Swift's 
important goal of ensuring that libraries only expose API surface they're 
committed to supporting indefinitely.

Basically, I think that either we need a new access level meaning "visible to 
the top-level module and all of its submodules, but not to other modules", or 
we need a way to specify that a submodule is internal-only and shouldn't be 
importable by outside code. My submodule sketch the other day took the second 
approach, but I think one or the other is necessary if we want submodules to 
serve both as public units of API surface and private encapsulators of 
implementation detail.

-- 
Brent Royal-Gordon
Architechies

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Xiaodi Wu via swift-evolution
On Tue, Feb 21, 2017 at 8:22 PM, Robert Widmann 
wrote:

>
> On Feb 21, 2017, at 9:13 PM, Xiaodi Wu  wrote:
>
> On Tue, Feb 21, 2017 at 7:59 PM, Robert Widmann via swift-evolution <
> swift-evolution@swift.org> wrote:
>
>>
>> On Feb 21, 2017, at 7:36 PM, Nevin Brackett-Rozinsky via swift-evolution <
>> swift-evolution@swift.org> wrote:
>>
>> To my mind, any submodule system for Swift should be designed to relieve
>> the pressure for long files, and make it easy to group tightly related
>> files into a single unit with shared visibility. That way developers can
>> easily organize their code into smaller files while utilizing Swift’s
>> pattern of providing protocol conformances in extensions and keeping
>> implementation details hidden from the rest of the module at large.
>>
>>
>> Wonderful, because that’s absolutely supported by this proposal.  To
>> group tightly related files into a single unit, simply declare a submodule
>> for them and extend it in each of your related files.
>>
>
> It's supported, but it isn't first-class. By this I mean: there are two
> distinguishable uses supported by your proposal, lumped together by the
> fact that they are both about grouping units of code together. Put crudely,
> one use case is grouping lines of code, while the other is about grouping
> files of code. The merits of supporting both have already been debated in
> this discussion. The issue I'll touch on is supporting both with the same
> syntax. The chief drawbacks here are:
>
>
> What exactly would be required to *make* it first class?  Referencing
> file names in the module declaration?
>

 See below.

> - It makes sense to use braces to group lines of code, but it makes no
> sense to use braces to group files of code; this just causes entire files
> to be indented.
>
>
> If braces aren’t used to demarcate scopes, nesting modules becomes
> ambiguous.
>

Again, let's observe the distinction about grouping files vs. grouping
lines.

Grouping files does not require braces: if the intended use of your feature
were to label files X, Y, and Z as belonging to one submodule and A, B, and
C to another, it would not matter if X, Y, and Z belonged to Foo.Bar and A,
B, and C to Foo.Bar.Baz: your syntax would not require braces.


> It’s important to note that indentation is one particular style.  LLVM
> code style, in particular, chooses not to indent after namespace
> declarations.  This issue also crops up when dealing with nested type
> declarations, and I distinctly remember it not being a big enough deal to
> "fix this" at the time when a proposal to “flatten” these declaration was
> brought up.
>

Mine is not a critique of the syntax itself; I don't particularly care
about indents, nor do I mind not indenting namespaces.

What I'm saying is, you would not have chosen to require braces if your
proposed feature were aimed at making the grouping of files into submodules
as simple as possible. You chose to accommodate grouping lines using the
same syntax as grouping files over the simplest design for grouping files.
Make no mistake, this promotes one use over another.

- Because some lines of code necessarily precede some other lines of code,
> it makes sense to declare the first group using `module` and to extend that
> with the second group using `extension`. However, because a file of code
> does not necessarily precede another file of code, it is arbitrary which
> file is surrounded with a `module` declaration and which one is surrounded
> with an `extension` declaration.
>
>
> Absolutely.  But it is similarly arbitrary which public APIs are exposed
> in a type declaration and which are exposed in an extension declaration.
>

Not entirely, no. Stored properties must be in the type declaration. Enum
cases must be in the type declaration. Perhaps you regard these as
temporary inconveniences of the current grammar; I see them as quite
reasonable ways to give some consistency as to what's written where in a
language where types can be retroactively extended. In a very real sense,
you must read the type declaration before you read the extensions in order
to understand the latter. By comparison, there is nothing that must be in
your proposed module declaration.


> My hope is that the module declaration itself will become the
> one-stop-shop for re-exports and general public bookkeeping just as
> aggregate declarations are today.  Module extensions exist to accommodate
> users that wish to break related functionality across files or into
> separate independent regions within the same file for the same reasons type
> extensions exist.
>

Indeed, that you phrase it this way supports Nevin's argument. _Module
extensions_ exist to accommodate his use case; however, his use case
(which, mind you, is what I think most people are thinking of when it comes
to submodules, given previous threads on this topic) isn't the raison
d'etre for your submodule proposal. Quite simply, a 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Robert Widmann via swift-evolution

> On Feb 21, 2017, at 9:13 PM, Xiaodi Wu  wrote:
> 
> On Tue, Feb 21, 2017 at 7:59 PM, Robert Widmann via swift-evolution 
> > wrote:
> 
>> On Feb 21, 2017, at 7:36 PM, Nevin Brackett-Rozinsky via swift-evolution 
>> > wrote:
>> 
>> To my mind, any submodule system for Swift should be designed to relieve the 
>> pressure for long files, and make it easy to group tightly related files 
>> into a single unit with shared visibility. That way developers can easily 
>> organize their code into smaller files while utilizing Swift’s pattern of 
>> providing protocol conformances in extensions and keeping implementation 
>> details hidden from the rest of the module at large.
>> 
> 
> Wonderful, because that’s absolutely supported by this proposal.  To group 
> tightly related files into a single unit, simply declare a submodule for them 
> and extend it in each of your related files.
> 
> It's supported, but it isn't first-class. By this I mean: there are two 
> distinguishable uses supported by your proposal, lumped together by the fact 
> that they are both about grouping units of code together. Put crudely, one 
> use case is grouping lines of code, while the other is about grouping files 
> of code. The merits of supporting both have already been debated in this 
> discussion. The issue I'll touch on is supporting both with the same syntax. 
> The chief drawbacks here are:
> 

What exactly would be required to make it first class?  Referencing file names 
in the module declaration?

> - It makes sense to use braces to group lines of code, but it makes no sense 
> to use braces to group files of code; this just causes entire files to be 
> indented.
> 

If braces aren’t used to demarcate scopes, nesting modules becomes ambiguous.  
It’s important to note that indentation is one particular style.  LLVM code 
style, in particular, chooses not to indent after namespace declarations.  This 
issue also crops up when dealing with nested type declarations, and I 
distinctly remember it not being a big enough deal to "fix this" at the time 
when a proposal to “flatten” these declaration was brought up.

> - Because some lines of code necessarily precede some other lines of code, it 
> makes sense to declare the first group using `module` and to extend that with 
> the second group using `extension`. However, because a file of code does not 
> necessarily precede another file of code, it is arbitrary which file is 
> surrounded with a `module` declaration and which one is surrounded with an 
> `extension` declaration.

Absolutely.  But it is similarly arbitrary which public APIs are exposed in a 
type declaration and which are exposed in an extension declaration.  My hope is 
that the module declaration itself will become the one-stop-shop for re-exports 
and general public bookkeeping just as aggregate declarations are today.  
Module extensions exist to accommodate users that wish to break related 
functionality across files or into separate independent regions within the same 
file for the same reasons type extensions exist.


> 
> Any variables defined with `internal` access will be visible across those 
> files to those extensions and only those extensions (see the section on 
> access control and modules).  Any variables declared fileprivate or private 
> will, obviously, not be visible across these files.  As an example:
> 
> // FooUtilities.swift
> //
> // -module-name=Foo
> // module Foo {
> // Defines Foo.Utilities
> module Utilities {
>   public func exportableOutsideThisSubmodule() {}
>   func visibleInThisSubmodule() {}
>   private func invisibleToOtherFiles() {}
> }
> //}
> 
> // FooUtilities+MoreUtilities.swift
> extension Utilities {
>   private func privateHelper() {
> visibleInThisSubmodule()
>   }
> }
> 
> I’m not sure where you got the impression that we were just trying to make 
> another fileprivate happen.
> 
>> 
>> Nevin
>> ___
>> swift-evolution mailing list
>> swift-evolution@swift.org 
>> https://lists.swift.org/mailman/listinfo/swift-evolution 
>> 
> 
> 
> ___
> swift-evolution mailing list
> swift-evolution@swift.org 
> https://lists.swift.org/mailman/listinfo/swift-evolution 
> 
___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Xiaodi Wu via swift-evolution
On Tue, Feb 21, 2017 at 8:15 PM, Robert Widmann via swift-evolution <
swift-evolution@swift.org> wrote:

>
> On Feb 21, 2017, at 7:46 AM, Brent Royal-Gordon via swift-evolution <
> swift-evolution@swift.org> wrote:
>
> On Feb 21, 2017, at 1:28 AM, Daniel Duan via swift-evolution <
> swift-evolution@swift.org> wrote:
>
> It has been my hope that a lightweight module system will remove the need
> for `private` *and* `fileprivate`.
>
>
> I really doubt it will. `private`/`fileprivate` works because you can also
> access `internal` at the same time.
>
> What I mean by that is, think about code like this:
>
> // Foo.swift
> public class Foo {
> public init() { … }
>
> func doBar() -> Quux {
> return helper(in: randomRange())
> }
>
> private func helper(in range: Range) -> Quux {
> …
> }
> }
>
> // Bar.swift
> public class Bar {
> public static let shared = Bar()
>
> func baz(with foo: Foo) {
> let quux = foo.doBar()
> process(quux)
> }
>
> private func process(_ quux: Quux) {
> …
> }
> }
>
> These classes have `public` APIs that are externally visible, `internal`
> APIs for communicating with each other, and `private` APIs for
> implementation details. Now try to reproduce the same design with
> submodules and `public`/`internal` only:
>
> public import MyMod.Foo
> public import MyMod.Bar
>
> module Foo {
> public class Foo {
> public init() { … }
>
>
> ??? func doBar() -> Quux {
> return helper(in: randomRange())
> }
>
> func helper(in range: Range) -> Quux {
> …
> }
> }
> }
>
> // Bar.swift
> module Bar {
> public class Bar {
> public static let shared = Bar()
>
> ??? func baz(with foo: Foo) {
> let quux = foo.doBar()
> process(quux)
> }
>
> func process(_ quux: Quux) {
> …
> }
> }
> }
>
> The `doBar()` and `baz()` methods have to be either exposed to third
> parties or kept away from yourself. That's just not viable.
>
>
> If they must communicate, they can be a part of the same (sub)module.
> This makes filling in these annotations trivial.  Nobody actually uses
> modules to wall off their own APIs from themselves like this, they use
> submodules to encapsulate the internal parts and surface public APIs in the
> parent.
>

I think you'll find a ton of people on this list who would want to use
submodules precisely to wall off their own APIs from themselves. Witness
the hundreds of messages about new syntax to do just that.


>
> module Bar {
>
> public class Foo {
>
> public init() { … }
>
>
>
> internal func doBar() -> Quux {
>
> return helper(in: randomRange())
>
> }
>
>
> internal func helper(in range: Range) -> Quux {
>
> …
>
> }
>
> }
>
> }
>
>
> // Bar.swift
>
> extension Bar {
>
> public class Bar {
>
> public static let shared = Bar()
>
>
> internal func baz(with foo: Foo) {
>
> let quux = foo.doBar()
>
> process(quux)
>
> }
>
>
> internal func process(_ quux: Quux) {
>
> …
>
> }
>
> }
> }
>
> --
> Brent Royal-Gordon
> Architechies
>
> ___
> swift-evolution mailing list
> swift-evolution@swift.org
> https://lists.swift.org/mailman/listinfo/swift-evolution
>
>
>
> ___
> swift-evolution mailing list
> swift-evolution@swift.org
> https://lists.swift.org/mailman/listinfo/swift-evolution
>
>
___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Robert Widmann via swift-evolution

> On Feb 21, 2017, at 7:46 AM, Brent Royal-Gordon via swift-evolution 
>  wrote:
> 
>> On Feb 21, 2017, at 1:28 AM, Daniel Duan via swift-evolution 
>>  wrote:
>> 
>> It has been my hope that a lightweight module system will remove the need 
>> for `private` *and* `fileprivate`.
> 
> I really doubt it will. `private`/`fileprivate` works because you can also 
> access `internal` at the same time.
> 
> What I mean by that is, think about code like this:
> 
>   // Foo.swift
>   public class Foo {
>   public init() { … }
> 
>   func doBar() -> Quux {
>   return helper(in: randomRange())
>   }
> 
>   private func helper(in range: Range) -> Quux {
>   …
>   }
>   }
> 
>   // Bar.swift
>   public class Bar {
>   public static let shared = Bar()
> 
>   func baz(with foo: Foo) {
>   let quux = foo.doBar()
>   process(quux)
>   }
>   
>   private func process(_ quux: Quux) {
>   …
>   }
>   }
> 
> These classes have `public` APIs that are externally visible, `internal` APIs 
> for communicating with each other, and `private` APIs for implementation 
> details. Now try to reproduce the same design with submodules and 
> `public`/`internal` only:
> 
>   public import MyMod.Foo
>   public import MyMod.Bar
> 
>   module Foo {
>   public class Foo {
>   public init() { … }
> 
> 
>   ??? func doBar() -> Quux {
>   return helper(in: randomRange())
>   }
> 
>   func helper(in range: Range) -> Quux {
>   …
>   }
>   }
>   }
> 
>   // Bar.swift
>   module Bar {
>   public class Bar {
>   public static let shared = Bar()
>   
>   ??? func baz(with foo: Foo) {
>   let quux = foo.doBar()
>   process(quux)
>   }
>   
>   func process(_ quux: Quux) {
>   …
>   }
>   }
>   }
> 
> The `doBar()` and `baz()` methods have to be either exposed to third parties 
> or kept away from yourself. That's just not viable.
> 

If they must communicate, they can be a part of the same (sub)module.  This 
makes filling in these annotations trivial.  Nobody actually uses modules to 
wall off their own APIs from themselves like this, they use submodules to 
encapsulate the internal parts and surface public APIs in the parent.

module Bar {
public class Foo {
public init() { … }


internal func doBar() -> Quux {
return helper(in: randomRange())
}

internal func helper(in range: Range) -> Quux {
…
}
}
}

// Bar.swift
extension Bar {
public class Bar {
public static let shared = Bar()

internal func baz(with foo: Foo) {
let quux = foo.doBar()
process(quux)
}

internal func process(_ quux: Quux) {
…
}
}
}

> -- 
> Brent Royal-Gordon
> Architechies
> 
> ___
> swift-evolution mailing list
> swift-evolution@swift.org
> https://lists.swift.org/mailman/listinfo/swift-evolution

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Xiaodi Wu via swift-evolution
On Tue, Feb 21, 2017 at 7:59 PM, Robert Widmann via swift-evolution <
swift-evolution@swift.org> wrote:

>
> On Feb 21, 2017, at 7:36 PM, Nevin Brackett-Rozinsky via swift-evolution <
> swift-evolution@swift.org> wrote:
>
> To my mind, any submodule system for Swift should be designed to relieve
> the pressure for long files, and make it easy to group tightly related
> files into a single unit with shared visibility. That way developers can
> easily organize their code into smaller files while utilizing Swift’s
> pattern of providing protocol conformances in extensions and keeping
> implementation details hidden from the rest of the module at large.
>
>
> Wonderful, because that’s absolutely supported by this proposal.  To group
> tightly related files into a single unit, simply declare a submodule for
> them and extend it in each of your related files.
>

It's supported, but it isn't first-class. By this I mean: there are two
distinguishable uses supported by your proposal, lumped together by the
fact that they are both about grouping units of code together. Put crudely,
one use case is grouping lines of code, while the other is about grouping
files of code. The merits of supporting both have already been debated in
this discussion. The issue I'll touch on is supporting both with the same
syntax. The chief drawbacks here are:

- It makes sense to use braces to group lines of code, but it makes no
sense to use braces to group files of code; this just causes entire files
to be indented.

- Because some lines of code necessarily precede some other lines of code,
it makes sense to declare the first group using `module` and to extend that
with the second group using `extension`. However, because a file of code
does not necessarily precede another file of code, it is arbitrary which
file is surrounded with a `module` declaration and which one is surrounded
with an `extension` declaration.

In both of these cases, your proposal has chosen to accommodate grouping
lines of code over the ergonomics of grouping files of code. Therefore,
while Nevin's use case is "absolutely supported by this proposal," I agree
with him that your choices promote something else entirely.


Any variables defined with `internal` access will be visible across those
> files to those extensions and only those extensions (see the section on
> access control and modules).  Any variables declared fileprivate or private
> will, obviously, not be visible across these files.  As an example:
>
> // FooUtilities.swift
> //
> // -module-name=Foo
> // module Foo {
> // Defines Foo.Utilities
> module Utilities {
>   public func exportableOutsideThisSubmodule() {}
>   func visibleInThisSubmodule() {}
>   private func invisibleToOtherFiles() {}
> }
> //}
>
> // FooUtilities+MoreUtilities.swift
> extension Utilities {
>   private func privateHelper() {
> visibleInThisSubmodule()
>   }
> }
>
> I’m not sure where you got the impression that we were just trying to make
> another fileprivate happen.
>
>
> Nevin
> ___
> swift-evolution mailing list
> swift-evolution@swift.org
> https://lists.swift.org/mailman/listinfo/swift-evolution
>
>
>
> ___
> swift-evolution mailing list
> swift-evolution@swift.org
> https://lists.swift.org/mailman/listinfo/swift-evolution
>
>
___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Robert Widmann via swift-evolution

> On Feb 21, 2017, at 8:00 AM, Brent Royal-Gordon  
> wrote:
> 
>> On Feb 20, 2017, at 5:56 PM, Robert Widmann via swift-evolution 
>>  wrote:
>> 
>> The semantics of some existing access control modifiers shall also be 
>> extended to support module declarations:
>> 
>>  • open and public declarations are exported by a module for consumption 
>> by clients of the module.
>>  • internal declarations scope over the entire module and any derived 
>> submodules.
> 
> If I'm reading this correctly, you're proposing that the `internal` APIs in a 
> submodule should *not* be accessible to enclosing modules. I also don't see 
> any indication that you can control who is allowed to import a particular 
> submodule.
> 
> That means that, if you use a submodule to encapsulate internal state, the 
> APIs that are available to the parent module are *also* available to any 
> rando who feels like importing your submodule. I don't think that's going to 
> be a tenable design.

If the state is truly internal, and you are using internal access control, this 
is impossible.  The internal state cannot cross the module boundary unless it 
is marked public.  If a “random” feels like importing my submodule, they will 
not have access to any symbols.

> 
> (I have a couple other objections—I think the keyword ought to be `submodule` 
> if you don't need a top-level `module` declaration, I think there's a lot to 
> be said for a single declaration covering the entire file, and I'm pretty 
> iffy on this entire approach anyway—but this seems like the most serious 
> problem of the bunch.)
> 
> -- 
> Brent Royal-Gordon
> Architechies
> 

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Robert Widmann via swift-evolution

> On Feb 21, 2017, at 7:36 PM, Nevin Brackett-Rozinsky via swift-evolution 
>  wrote:
> 
> To my mind, any submodule system for Swift should be designed to relieve the 
> pressure for long files, and make it easy to group tightly related files into 
> a single unit with shared visibility. That way developers can easily organize 
> their code into smaller files while utilizing Swift’s pattern of providing 
> protocol conformances in extensions and keeping implementation details hidden 
> from the rest of the module at large.
> 

Wonderful, because that’s absolutely supported by this proposal.  To group 
tightly related files into a single unit, simply declare a submodule for them 
and extend it in each of your related files.  Any variables defined with 
`internal` access will be visible across those files to those extensions and 
only those extensions (see the section on access control and modules).  Any 
variables declared fileprivate or private will, obviously, not be visible 
across these files.  As an example:

// FooUtilities.swift
//
// -module-name=Foo
// module Foo {
// Defines Foo.Utilities
module Utilities {
  public func exportableOutsideThisSubmodule() {}
  func visibleInThisSubmodule() {}
  private func invisibleToOtherFiles() {}
}
//}

// FooUtilities+MoreUtilities.swift
extension Utilities {
  private func privateHelper() {
visibleInThisSubmodule()
  }
}

I’m not sure where you got the impression that we were just trying to make 
another fileprivate happen.

> 
> Nevin
> ___
> swift-evolution mailing list
> swift-evolution@swift.org
> https://lists.swift.org/mailman/listinfo/swift-evolution

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Zach Waldowski via swift-evolution
I agree with Nevin’s points in large strokes, but I don’t think large files are 
the end of the world. I think an important takeaway idea from all the access 
control threads is that we need not provide facilities in the language to 
support antipatterns; we should more focus on how to encourage good patterns 
better.

On the face of it, I’m excited by the proposal; even if this isn’t the answer, 
we should seek to go down any road that removes fileprivate (and I mean remove 
- not just a new spelling) but preserves aspect the feature to please whatever 
it is that people like about that feature.

> On Feb 21, 2017, at 7:36 PM, Nevin Brackett-Rozinsky via swift-evolution 
>  wrote:
> 
> This proposal is definitely *not* what I want from a submodule system, 
> because it will exacerbate the problem of developers stuffing large amounts 
> of code into a single file.
> 
> The “fileprivate” keyword already encourages long files, because there is no 
> way to split up related components into separate files while retaining 
> encapsulation. And scope-based “private” is even worse of an offender, 
> because it requires nesting code inside the same *type declaration*, so you 
> can’t even benefit from extensions.
> 
> To my mind, any submodule system for Swift should be designed to relieve the 
> pressure for long files, and make it easy to group tightly related files into 
> a single unit with shared visibility. That way developers can easily organize 
> their code into smaller files while utilizing Swift’s pattern of providing 
> protocol conformances in extensions and keeping implementation details hidden 
> from the rest of the module at large.
> 
> For example, one possible design would enable us to replace both “private” 
> and “fileprivate” with a single new access level—probably spelled “private— 
> which restricts visibility to just the current submodule. That way it 
> provides all the benefits of “fileprivate” (implementation hiding and the 
> ability to use extensions) while also allowing code to be placed in separate 
> files rather than one large file.
> 
> Nevin
> ___
> swift-evolution mailing list
> swift-evolution@swift.org
> https://lists.swift.org/mailman/listinfo/swift-evolution

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Nevin Brackett-Rozinsky via swift-evolution
This proposal is definitely *not* what I want from a submodule system,
because it will exacerbate the problem of developers stuffing large amounts
of code into a single file.

The “fileprivate” keyword already encourages long files, because there is
no way to split up related components into separate files while retaining
encapsulation. And scope-based “private” is even worse of an offender,
because it requires nesting code inside the same *type declaration*, so you
can’t even benefit from extensions.

To my mind, any submodule system for Swift should be designed to relieve
the pressure for long files, and make it easy to group tightly related
files into a single unit with shared visibility. That way developers can
easily organize their code into smaller files while utilizing Swift’s
pattern of providing protocol conformances in extensions and keeping
implementation details hidden from the rest of the module at large.

For example, one possible design would enable us to replace both “private”
and “fileprivate” with a single new access level—probably spelled
“private— which restricts visibility to just the current submodule. That
way it provides all the benefits of “fileprivate” (implementation hiding
and the ability to use extensions) while also allowing code to be placed in
separate files rather than one large file.

Nevin
___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Daniel Duan via swift-evolution
One pattern that lightweight module enables is a lot more free functions in 
place of methods. Because the functions would be encapsulated by a module and 
lose the polluting effect.


On Feb 21, 2017, at 4:46 AM, Brent Royal-Gordon via swift-evolution 
 wrote:

>> On Feb 21, 2017, at 1:28 AM, Daniel Duan via swift-evolution 
>>  wrote:
>> 
>> It has been my hope that a lightweight module system will remove the need 
>> for `private` *and* `fileprivate`.
> 
> I really doubt it will. `private`/`fileprivate` works because you can also 
> access `internal` at the same time.
> 
> What I mean by that is, think about code like this:
> 
>// Foo.swift
>public class Foo {
>public init() { … }
> 
>func doBar() -> Quux {
>return helper(in: randomRange())
>}
> 
>private func helper(in range: Range) -> Quux {
>…
>}
>}
> 
>// Bar.swift
>public class Bar {
>public static let shared = Bar()
> 
>func baz(with foo: Foo) {
>let quux = foo.doBar()
>process(quux)
>}
>
>private func process(_ quux: Quux) {
>…
>}
>}
> 
> These classes have `public` APIs that are externally visible, `internal` APIs 
> for communicating with each other, and `private` APIs for implementation 
> details. Now try to reproduce the same design with submodules and 
> `public`/`internal` only:
> 
>public import MyMod.Foo
>public import MyMod.Bar
> 
>module Foo {
>public class Foo {
>public init() { … }
> 
> 
>??? func doBar() -> Quux {
>return helper(in: randomRange())
>}
> 
>func helper(in range: Range) -> Quux {
>…
>}
>}
>}
> 
>// Bar.swift
>module Bar {
>public class Bar {
>public static let shared = Bar()
>
>??? func baz(with foo: Foo) {
>let quux = foo.doBar()
>process(quux)
>}
>
>func process(_ quux: Quux) {
>…
>}
>}
>}
> 
> The `doBar()` and `baz()` methods have to be either exposed to third parties 
> or kept away from yourself. That's just not viable.
> 
> -- 
> Brent Royal-Gordon
> Architechies
> 
> ___
> swift-evolution mailing list
> swift-evolution@swift.org
> https://lists.swift.org/mailman/listinfo/swift-evolution

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Jaden Geller via swift-evolution

> On Feb 21, 2017, at 5:00 AM, Brent Royal-Gordon via swift-evolution 
>  wrote:
> 
>> On Feb 20, 2017, at 5:56 PM, Robert Widmann via swift-evolution 
>>  wrote:
>> 
>> The semantics of some existing access control modifiers shall also be 
>> extended to support module declarations:
>> 
>>  • open and public declarations are exported by a module for consumption 
>> by clients of the module.
>>  • internal declarations scope over the entire module and any derived 
>> submodules.
> 
> If I'm reading this correctly, you're proposing that the `internal` APIs in a 
> submodule should *not* be accessible to enclosing modules. I also don't see 
> any indication that you can control who is allowed to import a particular 
> submodule.
> 
> That means that, if you use a submodule to encapsulate internal state, the 
> APIs that are available to the parent module are *also* available to any 
> rando who feels like importing your submodule. I don't think that's going to 
> be a tenable design.

It might be reasonable to allow access control modifiers to be used with 
modules.

— `private` module declarations can only be imported in the scope in which they 
were defined
— `fileprivate` module declarations can only be imported in the file in which 
they were defined
— `internal` module declarations can be imported anywhere in the outermost (?) 
module
— `public` module declaration are exported to consumers of the outermost module

Definitely more thought needs to go into this, but it might address this desire.

> 
> (I have a couple other objections—I think the keyword ought to be `submodule` 
> if you don't need a top-level `module` declaration, I think there's a lot to 
> be said for a single declaration covering the entire file, and I'm pretty 
> iffy on this entire approach anyway—but this seems like the most serious 
> problem of the bunch.)

I think using `submodule` as a keyword is both reasonable and a good idea. It 
does become problematic if/when we eventually want to allow entire files to be 
part of a submodule though…

> 
> -- 
> Brent Royal-Gordon
> Architechies
> 
> ___
> swift-evolution mailing list
> swift-evolution@swift.org
> https://lists.swift.org/mailman/listinfo/swift-evolution

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Brent Royal-Gordon via swift-evolution
> On Feb 20, 2017, at 5:56 PM, Robert Widmann via swift-evolution 
>  wrote:
> 
> The semantics of some existing access control modifiers shall also be 
> extended to support module declarations:
> 
>   • open and public declarations are exported by a module for consumption 
> by clients of the module.
>   • internal declarations scope over the entire module and any derived 
> submodules.

If I'm reading this correctly, you're proposing that the `internal` APIs in a 
submodule should *not* be accessible to enclosing modules. I also don't see any 
indication that you can control who is allowed to import a particular submodule.

That means that, if you use a submodule to encapsulate internal state, the APIs 
that are available to the parent module are *also* available to any rando who 
feels like importing your submodule. I don't think that's going to be a tenable 
design.

(I have a couple other objections—I think the keyword ought to be `submodule` 
if you don't need a top-level `module` declaration, I think there's a lot to be 
said for a single declaration covering the entire file, and I'm pretty iffy on 
this entire approach anyway—but this seems like the most serious problem of the 
bunch.)

-- 
Brent Royal-Gordon
Architechies

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Jaden Geller via swift-evolution

> On Feb 21, 2017, at 4:44 AM, Alex Blewitt  wrote:
> 
> 
>> On 21 Feb 2017, at 07:00, Jaden Geller via swift-evolution 
>>  wrote:
>> 
>> We avoid forcing users to organize code in such an opinionated manner just 
>> to please the compiler. Perhaps some submodules deserve a separate file, but 
>> I think that choice should not be forced by the language. I don’t have data 
>> on the popularity, but I personally very much dislike the similar 
>> restriction Java places on public classes and files.
> 
> On the other hand, having such standardisation means that you know exactly 
> where a type is based on its module membership. One of the outcomes of 
> Scala's move away from enforcing a relationship between files and their 
> module structure means that it is almost impossible to find where a type is 
> defined using the filesystem, and you resort to using 'git grep' or other 
> tools to find out where the implementation is located.
> 
>> Given that we want Swift to be a fantastic scripting language, I feel we 
>> ought not place artificial restrictions on code organization. Many scripts 
>> are a single file (for convenience) but may still benefit from the 
>> organization modules offer.
> 
> Is there a reason why a script should need to be in any module, as opposed to 
> a top-level/unnamed module?
> 

Submodules within a script provide encapsulation that can be useful for code 
organization. They likely would use an implicit (unnamed) outer module.

> Alex

Cheers,
Jaden
___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Brent Royal-Gordon via swift-evolution
> On Feb 21, 2017, at 1:28 AM, Daniel Duan via swift-evolution 
>  wrote:
> 
> It has been my hope that a lightweight module system will remove the need for 
> `private` *and* `fileprivate`.

I really doubt it will. `private`/`fileprivate` works because you can also 
access `internal` at the same time.

What I mean by that is, think about code like this:

// Foo.swift
public class Foo {
public init() { … }

func doBar() -> Quux {
return helper(in: randomRange())
}

private func helper(in range: Range) -> Quux {
…
}
}

// Bar.swift
public class Bar {
public static let shared = Bar()

func baz(with foo: Foo) {
let quux = foo.doBar()
process(quux)
}

private func process(_ quux: Quux) {
…
}
}

These classes have `public` APIs that are externally visible, `internal` APIs 
for communicating with each other, and `private` APIs for implementation 
details. Now try to reproduce the same design with submodules and 
`public`/`internal` only:

public import MyMod.Foo
public import MyMod.Bar

module Foo {
public class Foo {
public init() { … }


??? func doBar() -> Quux {
return helper(in: randomRange())
}

func helper(in range: Range) -> Quux {
…
}
}
}

// Bar.swift
module Bar {
public class Bar {
public static let shared = Bar()

??? func baz(with foo: Foo) {
let quux = foo.doBar()
process(quux)
}

func process(_ quux: Quux) {
…
}
}
}

The `doBar()` and `baz()` methods have to be either exposed to third parties or 
kept away from yourself. That's just not viable.

-- 
Brent Royal-Gordon
Architechies

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-21 Thread Alex Blewitt via swift-evolution

> On 21 Feb 2017, at 07:00, Jaden Geller via swift-evolution 
>  wrote:
> 
> We avoid forcing users to organize code in such an opinionated manner just to 
> please the compiler. Perhaps some submodules deserve a separate file, but I 
> think that choice should not be forced by the language. I don’t have data on 
> the popularity, but I personally very much dislike the similar restriction 
> Java places on public classes and files.

On the other hand, having such standardisation means that you know exactly 
where a type is based on its module membership. One of the outcomes of Scala's 
move away from enforcing a relationship between files and their module 
structure means that it is almost impossible to find where a type is defined 
using the filesystem, and you resort to using 'git grep' or other tools to find 
out where the implementation is located.

> Given that we want Swift to be a fantastic scripting language, I feel we 
> ought not place artificial restrictions on code organization. Many scripts 
> are a single file (for convenience) but may still benefit from the 
> organization modules offer.

Is there a reason why a script should need to be in any module, as opposed to a 
top-level/unnamed module?

Alex
___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-20 Thread Robert Widmann via swift-evolution


~Robert Widmann

2017/02/21 2:16、Jonathan Hull  のメッセージ:

> It is how it interacts with our current access control.  The scope based 
> nature of this will conflict with the file based nature of the stuff left 
> from Swift 2. I am convinced we need to overhaul it in one sweep to fit one 
> metaphor or the other. The more we mix them, the harder it is to wrap your 
> head around.  We can’t keep rehashing it every 6 months, but that is what 
> will happen so long as it stays in this confused state.

How does this conflict?  Moreover, what do you feel we are adding here that 
crosses the line?

This is not a rehash of existing concepts.  We do not deprecate the access 
control scheme, and we don't extend it except to define how symbols can 
indicate they wish to cross/not cross the module boundary.  This is genuinely a 
system to enable modularity at as little cost as we could suss out given 
inspiration from other programming languages. 

tl;dr I don't want to confuse this with the fileprivate debate.  It is possible 
to have physical access control and modularity, they're not mutually exclusive. 
 And the existing access control scheme cannot express the same concepts a real 
module system can, so it's not enough to paint this as a syntactic/physical 
argument.

> 
> I think I would prefer overall trying swift’s file based system because I 
> think we can completely close that with only 1-2 additional concepts (and it 
> would stay conceptually simple).  I would also be fine with switching to a 
> purely type/scope based system with protected, etc…, but I feel like that 
> will need more complexity to get it fully working (e.g. friends), and will 
> end up being a more complex system overall.

The semantics we intend are all there in the proposal.  You can see for 
yourself just how much this will complect the language versus a different 
proposal to redo access entirely.

> 
> Thanks,
> Jon
> 
> 
>>> On Feb 20, 2017, at 11:03 PM, Robert Widmann  
>>> wrote:
>>> 
>>> 
 On Feb 21, 2017, at 2:01 AM, Jonathan Hull  wrote:
 
 
 On Feb 20, 2017, at 10:46 PM, Robert Widmann via swift-evolution 
  wrote:
 
 More generally, we need to move access control away as far away from 
 filesystems as possible.  One day, the compiler is going to get ported 
 over to a platform with some bonkers rules that are going to turn around 
 and bite us.
>>> 
>>> This is the key thing which I think is being debated right now.  Swift 2 
>>> defined the file as a unit of compilation and based its elegant system of 
>>> access modifiers on that.  With Swift 3 we have a mix of type/scope based 
>>> modifiers and file based modifiers… and it is super confusing to everyone 
>>> because we have mixed our metaphors.
>>> 
>>> As much as I want modules, I am now convinced that this proposal will only 
>>> make that situation worse.  We need to pick one way (file based) or the 
>>> other (scope based) and commit to it… but either way, it will require a 
>>> larger overhaul to make the system consistent/usable/teachable again.
>>> 
>>> As an analogy, it is like some people are trying to play rock music during 
>>> a classical music concert.  Both are great independently, and different 
>>> people may prefer one or the other… but trying to play them on top of one 
>>> another just results in noise.
>> 
>> Is there anything specifically about this proposal that turns you off, or is 
>> it access control as it stands today?
>> 
>>> 
>>> Thanks,
>>> Jon
> 
___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-20 Thread Robert Widmann via swift-evolution
Sounds distressingly anti-modular!

Really, these kinds of hypotheticals can be addressed when the need arises.  
For now it's a hypothetical fear about a hypothetical issue that isn't 
expressible and highly discouraged by this system - why produce an inverted 
dependency when you could simply rebalance the module by moving the declaration 
into a more appropriate scope?  I can assure you, the proposal seeks 
compatibility with the existing access control modifiers, not to have to 
contort them to fit its own goals.

~Robert Widmann

2017/02/21 2:07、Jonathan Hull  のメッセージ:

> 
>> On Feb 20, 2017, at 10:51 PM, Robert Widmann
___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-20 Thread Jaden Geller via swift-evolution
It’s probably best we explain this motivation under “Alternatives Considered”. 
I forked and updated the gist—feel free to “pull” in the changes… copy 
and paste the document

https://gist.github.com/JadenGeller/c18b1be8e7b9fa3023e98b84fca423ca#multiple-declarations-instead-of-extensions
 


Cheers,
Jaden Geller

> On Feb 20, 2017, at 10:57 PM, Robert Widmann  wrote:
> 
> This was syntax I initially considered, but Jaden swayed me with the idea 
> that we already have an `extension` keyword so we may as well use it to match 
> the rest of the language.  Repeating the `module` declaration also lends 
> itself more to C++-style namespaces, which these are not.  I’m not saying 
> it’s out of the question, far from it. It is an alternative we will keep in 
> mind.
> 
> ~Robert Widmann
> 
>> On Feb 21, 2017, at 1:53 AM, Psycho Hedgehog via swift-evolution 
>> > wrote:
>> 
>> The one thing i don't understand is the point of using extensions to extend 
>> modules across multiple files, why not just allow declaring the submodule in 
>> multiple files?
>> 
>>> Le 20 févr. 2017 à 22:48, Jaden Geller via swift-evolution 
>>> > a écrit :
>>> 
>>> Oh, I see. You’re questioning the motivation of having scope-granularity 
>>> submodules at all! My misunderstanding.
>>> 
>>> I actually hadn’t considered this as added complexity. In my mind, a scoped 
>>> module declaration seems more Swifty than a file module declaration. It 
>>> builds on the existing syntax in Swift for defining other sorts of scopes, 
>>> e.g. types.
>>> 
>>> Cheers,
>>> Jaden Geller
>>> 
 On Feb 20, 2017, at 10:41 PM, Jonathan Hull via swift-evolution 
 > wrote:
 
 I think my question is: Why do we want to allow submodules that are 
 smaller than a file?  What does that give us to offset the added 
 complexity?
 
 Thanks,
 Jon
 
> On Feb 20, 2017, at 6:44 PM, Robert Widmann  > wrote:
> 
> 
>> On Feb 20, 2017, at 9:36 PM, Jonathan Hull > > wrote:
>> 
>> What is the rational for having modules covering only part of a file?  
>> Wouldn’t it be less clutter to have an annotation which worked for the 
>> whole file.  At the very least it would be nice to have an option to 
>> spell it in a way that applies to the whole file.  Otherwise, everything 
>> will be indented another level.
> 
> That is a valid spelling (Rust, IIRC, allows that spelling), but one that 
> is easy to miss sitting in a file and makes it confusing to introduce 
> submodules.  If you include the annotation then define a submodule later 
> down in the file, suddenly you have to remember whether you annotated the 
> file or whether the submodule you’ve just written is going into the 
> top-level module.  See:
> 
> // -module-name=Foo
> // module Foo {
> module Bar; // Shorthand for “This file defines Foo.Bar”
> 
> /* Code */
> 
> // This defines “Foo.Bar.Baz”, but would you know that if it appeared 
> below the fold?
> module Baz {}
> //}
> 
> If anything, this can be added later if evolution converges on it.
> 
>> 
>> I would honestly love to see something which just maps modules to 
>> folders/groups for simplicity sake.
>> 
> 
> There is nothing about this scheme that prevents you from organizing your 
> code this way.  However, modulo that particular method of organization, 
> you don’t really gain much as a user of the language by imposing this 
> restriction.
> 
>> I haven’t thought about it too much yet, so I could easily be missing 
>> something obvious...
>> 
>> Thanks,
>> Jon
>> 
>> 
>>> On Feb 20, 2017, at 5:56 PM, Robert Widmann via swift-evolution 
>>> > wrote:
>>> 
>>> Good Evening All,
>>> 
>>> Jaden Geller and I have been considering a (sub)module system for Swift 
>>> that would complement the existing language but also provide sorely 
>>> needed modularity.  A draft of the proposal is attached to this email, 
>>> but it can also be read as a gist 
>>>  if 
>>> you desire.
>>> 
>>> Cheers,
>>> 
>>> ~Robert Widmann
>>> 
>>> Modular Swift
>>> 
>>> Proposal: SE- 
>>> Authors: Robert Widmann , Jaden Geller 
>>> 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-20 Thread Robert Widmann via swift-evolution

> On Feb 21, 2017, at 2:01 AM, Jonathan Hull  wrote:
> 
> 
>> On Feb 20, 2017, at 10:46 PM, Robert Widmann via swift-evolution 
>> > wrote:
>> 
>> More generally, we need to move access control away as far away from 
>> filesystems as possible.  One day, the compiler is going to get ported over 
>> to a platform with some bonkers rules that are going to turn around and bite 
>> us.
> 
> This is the key thing which I think is being debated right now.  Swift 2 
> defined the file as a unit of compilation and based its elegant system of 
> access modifiers on that.  With Swift 3 we have a mix of type/scope based 
> modifiers and file based modifiers… and it is super confusing to everyone 
> because we have mixed our metaphors.
> 
> As much as I want modules, I am now convinced that this proposal will only 
> make that situation worse.  We need to pick one way (file based) or the other 
> (scope based) and commit to it… but either way, it will require a larger 
> overhaul to make the system consistent/usable/teachable again.
> 
> As an analogy, it is like some people are trying to play rock music during a 
> classical music concert.  Both are great independently, and different people 
> may prefer one or the other… but trying to play them on top of one another 
> just results in noise.

Is there anything specifically about this proposal that turns you off, or is it 
access control as it stands today?

> 
> Thanks,
> Jon
> 

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-20 Thread Jonathan Hull via swift-evolution

> On Feb 20, 2017, at 10:46 PM, Robert Widmann via swift-evolution 
>  wrote:
> 
> More generally, we need to move access control away as far away from 
> filesystems as possible.  One day, the compiler is going to get ported over 
> to a platform with some bonkers rules that are going to turn around and bite 
> us.

This is the key thing which I think is being debated right now.  Swift 2 
defined the file as a unit of compilation and based its elegant system of 
access modifiers on that.  With Swift 3 we have a mix of type/scope based 
modifiers and file based modifiers… and it is super confusing to everyone 
because we have mixed our metaphors.

As much as I want modules, I am now convinced that this proposal will only make 
that situation worse.  We need to pick one way (file based) or the other (scope 
based) and commit to it… but either way, it will require a larger overhaul to 
make the system consistent/usable/teachable again.

As an analogy, it is like some people are trying to play rock music during a 
classical music concert.  Both are great independently, and different people 
may prefer one or the other… but trying to play them on top of one another just 
results in noise.

Thanks,
Jon

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-20 Thread Jaden Geller via swift-evolution
We avoid forcing users to organize code in such an opinionated manner just to 
please the compiler. Perhaps some submodules deserve a separate file, but I 
think that choice should not be forced by the language. I don’t have data on 
the popularity, but I personally very much dislike the similar restriction Java 
places on public classes and files.

Given that we want Swift to be a fantastic scripting language, I feel we ought 
not place artificial restrictions on code organization. Many scripts are a 
single file (for convenience) but may still benefit from the organization 
modules offer.

Best,
Jaden Geller  

> On Feb 20, 2017, at 10:51 PM, Jonathan Hull  wrote:
> 
> Part of it.  My concern is that the brackets will push everything in the file 
> to the right.
> 
> My question is: What do we get in return for that? (as opposed to a system 
> which acted on the whole file)
> 
> Thanks,
> Jon
> 
> 
>> On Feb 20, 2017, at 10:45 PM, Jaden Geller > > wrote:
>> 
>> Oh, you’re referring to the fact that a submodule under this proposal must 
>> be contained within braces? It would be purely additive to, in the future, 
>> annotate that the outer scope of a file is part of some given submodule.
>> 
>> Consider the following the following straw-man syntax that might be 
>> equivalent to `module Bar { func foo() { } }`:
>> ```
>> module Bar follows // <- at top of file, indicating rest of file is submodule
>> 
>> func foo() { }
>> ```
>> 
>> Does this address your question?
>> 
>> Thanks,
>> Jaden Geller
>> 
>>> On Feb 20, 2017, at 10:39 PM, Jonathan Hull >> > wrote:
>>> 
>>> 
 On Feb 20, 2017, at 6:42 PM, Jaden Geller > wrote:
 
 Jon,
 
 I think we might have miscommunicated. It is intended that outermost 
 module is implicit; no `module` declaration is required to wrap every 
 file. We tried to show this in the first code snippet.
 
 What do you mean “covering only part of a file”?
>>> 
>>> I am assuming that the ModuleName { … }  only affects things within the 
>>> brackets.  Thus it is possible for only part of a file to be within a 
>>> module.  What are the benefits of allowing this, and are they worth the 
>>> added complexity?
>>> 
>>> Thanks,
>>> Jon
>>> 
>>> 
 Cheers,
 Jaden Geller
 
> On Feb 20, 2017, at 6:36 PM, Jonathan Hull via swift-evolution 
> > wrote:
> 
> What is the rational for having modules covering only part of a file?  
> Wouldn’t it be less clutter to have an annotation which worked for the 
> whole file.  At the very least it would be nice to have an option to 
> spell it in a way that applies to the whole file.  Otherwise, everything 
> will be indented another level.
> 
> I would honestly love to see something which just maps modules to 
> folders/groups for simplicity sake.
> 
> I haven’t thought about it too much yet, so I could easily be missing 
> something obvious...
> 
> Thanks,
> Jon
>>> 
>> 
> 

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-20 Thread Robert Widmann via swift-evolution
This was syntax I initially considered, but Jaden swayed me with the idea that 
we already have an `extension` keyword so we may as well use it to match the 
rest of the language.  Repeating the `module` declaration also lends itself 
more to C++-style namespaces, which these are not.  I’m not saying it’s out of 
the question, far from it. It is an alternative we will keep in mind.

~Robert Widmann

> On Feb 21, 2017, at 1:53 AM, Psycho Hedgehog via swift-evolution 
>  wrote:
> 
> The one thing i don't understand is the point of using extensions to extend 
> modules across multiple files, why not just allow declaring the submodule in 
> multiple files?
> 
>> Le 20 févr. 2017 à 22:48, Jaden Geller via swift-evolution 
>> > a écrit :
>> 
>> Oh, I see. You’re questioning the motivation of having scope-granularity 
>> submodules at all! My misunderstanding.
>> 
>> I actually hadn’t considered this as added complexity. In my mind, a scoped 
>> module declaration seems more Swifty than a file module declaration. It 
>> builds on the existing syntax in Swift for defining other sorts of scopes, 
>> e.g. types.
>> 
>> Cheers,
>> Jaden Geller
>> 
>>> On Feb 20, 2017, at 10:41 PM, Jonathan Hull via swift-evolution 
>>> > wrote:
>>> 
>>> I think my question is: Why do we want to allow submodules that are smaller 
>>> than a file?  What does that give us to offset the added complexity?
>>> 
>>> Thanks,
>>> Jon
>>> 
 On Feb 20, 2017, at 6:44 PM, Robert Widmann > wrote:
 
 
> On Feb 20, 2017, at 9:36 PM, Jonathan Hull  > wrote:
> 
> What is the rational for having modules covering only part of a file?  
> Wouldn’t it be less clutter to have an annotation which worked for the 
> whole file.  At the very least it would be nice to have an option to 
> spell it in a way that applies to the whole file.  Otherwise, everything 
> will be indented another level.
 
 That is a valid spelling (Rust, IIRC, allows that spelling), but one that 
 is easy to miss sitting in a file and makes it confusing to introduce 
 submodules.  If you include the annotation then define a submodule later 
 down in the file, suddenly you have to remember whether you annotated the 
 file or whether the submodule you’ve just written is going into the 
 top-level module.  See:
 
 // -module-name=Foo
 // module Foo {
 module Bar; // Shorthand for “This file defines Foo.Bar”
 
 /* Code */
 
 // This defines “Foo.Bar.Baz”, but would you know that if it appeared 
 below the fold?
 module Baz {}
 //}
 
 If anything, this can be added later if evolution converges on it.
 
> 
> I would honestly love to see something which just maps modules to 
> folders/groups for simplicity sake.
> 
 
 There is nothing about this scheme that prevents you from organizing your 
 code this way.  However, modulo that particular method of organization, 
 you don’t really gain much as a user of the language by imposing this 
 restriction.
 
> I haven’t thought about it too much yet, so I could easily be missing 
> something obvious...
> 
> Thanks,
> Jon
> 
> 
>> On Feb 20, 2017, at 5:56 PM, Robert Widmann via swift-evolution 
>> > wrote:
>> 
>> Good Evening All,
>> 
>> Jaden Geller and I have been considering a (sub)module system for Swift 
>> that would complement the existing language but also provide sorely 
>> needed modularity.  A draft of the proposal is attached to this email, 
>> but it can also be read as a gist 
>>  if you 
>> desire.
>> 
>> Cheers,
>> 
>> ~Robert Widmann
>> 
>> Modular Swift
>> 
>> Proposal: SE- 
>> Authors: Robert Widmann , Jaden Geller 
>> 
>> Review Manager: TBD
>> Status: Awaiting review
>>  
>> Introduction
>> 
>> Almost every major programming language supports some form of modular 
>> programming through constructs like (sub)modules, packages, or 
>> interfaces. Swift, though it provides top-level modules to organize code 
>> under, does not provide a complete implementation of any of these 
>> concepts, which has led instead to the proliferation of access control 
>> levels. This has not proven an effective way to decompose programs into 
>> manageable parts, and 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-20 Thread Psycho Hedgehog via swift-evolution
The one thing i don't understand is the point of using extensions to extend 
modules across multiple files, why not just allow declaring the submodule in 
multiple files?

> Le 20 févr. 2017 à 22:48, Jaden Geller via swift-evolution 
>  a écrit :
> 
> Oh, I see. You’re questioning the motivation of having scope-granularity 
> submodules at all! My misunderstanding.
> 
> I actually hadn’t considered this as added complexity. In my mind, a scoped 
> module declaration seems more Swifty than a file module declaration. It 
> builds on the existing syntax in Swift for defining other sorts of scopes, 
> e.g. types.
> 
> Cheers,
> Jaden Geller
> 
>> On Feb 20, 2017, at 10:41 PM, Jonathan Hull via swift-evolution 
>> > wrote:
>> 
>> I think my question is: Why do we want to allow submodules that are smaller 
>> than a file?  What does that give us to offset the added complexity?
>> 
>> Thanks,
>> Jon
>> 
>>> On Feb 20, 2017, at 6:44 PM, Robert Widmann >> > wrote:
>>> 
>>> 
 On Feb 20, 2017, at 9:36 PM, Jonathan Hull > wrote:
 
 What is the rational for having modules covering only part of a file?  
 Wouldn’t it be less clutter to have an annotation which worked for the 
 whole file.  At the very least it would be nice to have an option to spell 
 it in a way that applies to the whole file.  Otherwise, everything will be 
 indented another level.
>>> 
>>> That is a valid spelling (Rust, IIRC, allows that spelling), but one that 
>>> is easy to miss sitting in a file and makes it confusing to introduce 
>>> submodules.  If you include the annotation then define a submodule later 
>>> down in the file, suddenly you have to remember whether you annotated the 
>>> file or whether the submodule you’ve just written is going into the 
>>> top-level module.  See:
>>> 
>>> // -module-name=Foo
>>> // module Foo {
>>> module Bar; // Shorthand for “This file defines Foo.Bar”
>>> 
>>> /* Code */
>>> 
>>> // This defines “Foo.Bar.Baz”, but would you know that if it appeared below 
>>> the fold?
>>> module Baz {}
>>> //}
>>> 
>>> If anything, this can be added later if evolution converges on it.
>>> 
 
 I would honestly love to see something which just maps modules to 
 folders/groups for simplicity sake.
 
>>> 
>>> There is nothing about this scheme that prevents you from organizing your 
>>> code this way.  However, modulo that particular method of organization, you 
>>> don’t really gain much as a user of the language by imposing this 
>>> restriction.
>>> 
 I haven’t thought about it too much yet, so I could easily be missing 
 something obvious...
 
 Thanks,
 Jon
 
 
> On Feb 20, 2017, at 5:56 PM, Robert Widmann via swift-evolution 
> > wrote:
> 
> Good Evening All,
> 
> Jaden Geller and I have been considering a (sub)module system for Swift 
> that would complement the existing language but also provide sorely 
> needed modularity.  A draft of the proposal is attached to this email, 
> but it can also be read as a gist 
>  if you 
> desire.
> 
> Cheers,
> 
> ~Robert Widmann
> 
> Modular Swift
> 
> Proposal: SE- 
> Authors: Robert Widmann , Jaden Geller 
> 
> Review Manager: TBD
> Status: Awaiting review
>  
> Introduction
> 
> Almost every major programming language supports some form of modular 
> programming through constructs like (sub)modules, packages, or 
> interfaces. Swift, though it provides top-level modules to organize code 
> under, does not provide a complete implementation of any of these 
> concepts, which has led instead to the proliferation of access control 
> levels. This has not proven an effective way to decompose programs into 
> manageable parts, and exposes the need for a real system of modules to 
> solve this modularity problem once and for all.
> 
> Separation of code into distinct islands of functionality should be a 
> first-class construct in the language, not dependent on external files 
> and tools or filesystems. To that end, we propose the introduction of a 
> lightweight module system for Swift.
> 
> Swift-evolution thread 
> 
>  
> Motivation
> 
> Swift has reached a point in its evolution where rich libraries and large 
> projects that take on many 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-20 Thread Jonathan Hull via swift-evolution
Part of it.  My concern is that the brackets will push everything in the file 
to the right.

My question is: What do we get in return for that? (as opposed to a system 
which acted on the whole file)

Thanks,
Jon


> On Feb 20, 2017, at 10:45 PM, Jaden Geller  wrote:
> 
> Oh, you’re referring to the fact that a submodule under this proposal must be 
> contained within braces? It would be purely additive to, in the future, 
> annotate that the outer scope of a file is part of some given submodule.
> 
> Consider the following the following straw-man syntax that might be 
> equivalent to `module Bar { func foo() { } }`:
> ```
> module Bar follows // <- at top of file, indicating rest of file is submodule
> 
> func foo() { }
> ```
> 
> Does this address your question?
> 
> Thanks,
> Jaden Geller
> 
>> On Feb 20, 2017, at 10:39 PM, Jonathan Hull > > wrote:
>> 
>> 
>>> On Feb 20, 2017, at 6:42 PM, Jaden Geller >> > wrote:
>>> 
>>> Jon,
>>> 
>>> I think we might have miscommunicated. It is intended that outermost module 
>>> is implicit; no `module` declaration is required to wrap every file. We 
>>> tried to show this in the first code snippet.
>>> 
>>> What do you mean “covering only part of a file”?
>> 
>> I am assuming that the ModuleName { … }  only affects things within the 
>> brackets.  Thus it is possible for only part of a file to be within a 
>> module.  What are the benefits of allowing this, and are they worth the 
>> added complexity?
>> 
>> Thanks,
>> Jon
>> 
>> 
>>> Cheers,
>>> Jaden Geller
>>> 
 On Feb 20, 2017, at 6:36 PM, Jonathan Hull via swift-evolution 
 > wrote:
 
 What is the rational for having modules covering only part of a file?  
 Wouldn’t it be less clutter to have an annotation which worked for the 
 whole file.  At the very least it would be nice to have an option to spell 
 it in a way that applies to the whole file.  Otherwise, everything will be 
 indented another level.
 
 I would honestly love to see something which just maps modules to 
 folders/groups for simplicity sake.
 
 I haven’t thought about it too much yet, so I could easily be missing 
 something obvious...
 
 Thanks,
 Jon
>> 
> 

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-20 Thread Robert Widmann via swift-evolution

> On Feb 21, 2017, at 1:46 AM, Jonathan Hull  wrote:
> 
> 
>> On Feb 20, 2017, at 6:44 PM, Robert Widmann > > wrote:
>> 
>>> 
>>> 
>>> I would honestly love to see something which just maps modules to 
>>> folders/groups for simplicity sake.
>>> 
>> 
>> There is nothing about this scheme that prevents you from organizing your 
>> code this way.  However, modulo that particular method of organization, you 
>> don’t really gain much as a user of the language by imposing this 
>> restriction.
> 
> I think the big gain is that users of IDEs would just be able to graphically 
> organize modules in Xcode.  Non-IDE users could use the finder to organize 
> things into nested folders.  This maps pretty well with the way I organize my 
> code already (others may be different), so it doesn’t add much complexity.
> 

Xcode today is able to do this with nested classes and structures with the 
hierarchy navigator.  Non-IDE users can use grep or (hopefully) some 
syntax-aware plugin system to help them find these declarations.  Really, 
again, this is a design pattern and one that can be enforced by linters.  If we 
were to impose this restriction at the language level it ties this proposal 
down to file system structure and we are explicitly trying to avoid that.

> On a side note, I do think that people will quickly want a way to reference a 
> particular submodule boundary with access modifiers.  It may not be part of 
> this proposal, but it is somewhat inevitable.  We should consider that as we 
> consider this proposal…
> 

Modules are not types, access control makes no sense here.  APIs may be 
exported (or not) across module boundaries, but modules themselves are not 
arbitrary programming constructs nor do we consider them to carry semantic 
weight as in some other ML-likes.  A public module is no different from a 
private module if you can import it.  A private module is no different from a 
public one if you cannot.

> Thanks,
> Jon

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-20 Thread Jaden Geller via swift-evolution
Oh, I see. You’re questioning the motivation of having scope-granularity 
submodules at all! My misunderstanding.

I actually hadn’t considered this as added complexity. In my mind, a scoped 
module declaration seems more Swifty than a file module declaration. It builds 
on the existing syntax in Swift for defining other sorts of scopes, e.g. types.

Cheers,
Jaden Geller

> On Feb 20, 2017, at 10:41 PM, Jonathan Hull via swift-evolution 
>  wrote:
> 
> I think my question is: Why do we want to allow submodules that are smaller 
> than a file?  What does that give us to offset the added complexity?
> 
> Thanks,
> Jon
> 
>> On Feb 20, 2017, at 6:44 PM, Robert Widmann > > wrote:
>> 
>> 
>>> On Feb 20, 2017, at 9:36 PM, Jonathan Hull >> > wrote:
>>> 
>>> What is the rational for having modules covering only part of a file?  
>>> Wouldn’t it be less clutter to have an annotation which worked for the 
>>> whole file.  At the very least it would be nice to have an option to spell 
>>> it in a way that applies to the whole file.  Otherwise, everything will be 
>>> indented another level.
>> 
>> That is a valid spelling (Rust, IIRC, allows that spelling), but one that is 
>> easy to miss sitting in a file and makes it confusing to introduce 
>> submodules.  If you include the annotation then define a submodule later 
>> down in the file, suddenly you have to remember whether you annotated the 
>> file or whether the submodule you’ve just written is going into the 
>> top-level module.  See:
>> 
>> // -module-name=Foo
>> // module Foo {
>> module Bar; // Shorthand for “This file defines Foo.Bar”
>> 
>> /* Code */
>> 
>> // This defines “Foo.Bar.Baz”, but would you know that if it appeared below 
>> the fold?
>> module Baz {}
>> //}
>> 
>> If anything, this can be added later if evolution converges on it.
>> 
>>> 
>>> I would honestly love to see something which just maps modules to 
>>> folders/groups for simplicity sake.
>>> 
>> 
>> There is nothing about this scheme that prevents you from organizing your 
>> code this way.  However, modulo that particular method of organization, you 
>> don’t really gain much as a user of the language by imposing this 
>> restriction.
>> 
>>> I haven’t thought about it too much yet, so I could easily be missing 
>>> something obvious...
>>> 
>>> Thanks,
>>> Jon
>>> 
>>> 
 On Feb 20, 2017, at 5:56 PM, Robert Widmann via swift-evolution 
 > wrote:
 
 Good Evening All,
 
 Jaden Geller and I have been considering a (sub)module system for Swift 
 that would complement the existing language but also provide sorely needed 
 modularity.  A draft of the proposal is attached to this email, but it can 
 also be read as a gist 
  if you 
 desire.
 
 Cheers,
 
 ~Robert Widmann
 
 Modular Swift
 
 Proposal: SE- 
 Authors: Robert Widmann , Jaden Geller 
 
 Review Manager: TBD
 Status: Awaiting review
  
 Introduction
 
 Almost every major programming language supports some form of modular 
 programming through constructs like (sub)modules, packages, or interfaces. 
 Swift, though it provides top-level modules to organize code under, does 
 not provide a complete implementation of any of these concepts, which has 
 led instead to the proliferation of access control levels. This has not 
 proven an effective way to decompose programs into manageable parts, and 
 exposes the need for a real system of modules to solve this modularity 
 problem once and for all.
 
 Separation of code into distinct islands of functionality should be a 
 first-class construct in the language, not dependent on external files and 
 tools or filesystems. To that end, we propose the introduction of a 
 lightweight module system for Swift.
 
 Swift-evolution thread 
 
  
 Motivation
 
 Swift has reached a point in its evolution where rich libraries and large 
 projects that take on many dependencies have matured significantly. To 
 accomodate the information-hiding and semantics-signalling needs of these 
 users at the time, Swift began its access control story with just three 
 access modifiers: public, private, and internal then grew fileprivate and 
 open as the need to express locality of implementation and 
 "subclassability" arose respectively. In doing so, Swift's access control 
 scheme has 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-20 Thread Jonathan Hull via swift-evolution

> On Feb 20, 2017, at 6:44 PM, Robert Widmann  wrote:
> 
>> 
>> 
>> I would honestly love to see something which just maps modules to 
>> folders/groups for simplicity sake.
>> 
> 
> There is nothing about this scheme that prevents you from organizing your 
> code this way.  However, modulo that particular method of organization, you 
> don’t really gain much as a user of the language by imposing this restriction.

I think the big gain is that users of IDEs would just be able to graphically 
organize modules in Xcode.  Non-IDE users could use the finder to organize 
things into nested folders.  This maps pretty well with the way I organize my 
code already (others may be different), so it doesn’t add much complexity.

On a side note, I do think that people will quickly want a way to reference a 
particular submodule boundary with access modifiers.  It may not be part of 
this proposal, but it is somewhat inevitable.  We should consider that as we 
consider this proposal…

Thanks,
Jon___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-20 Thread Robert Widmann via swift-evolution

> On Feb 20, 2017, at 11:39 PM, Matthew Johnson  wrote:
> 
> Thanks for bringing up submodules Robert.  I agree it's a good time to 
> discuss them.  
> 
> There seem to be two broad approaches to submodules.  One is more of a 
> physical / encapsulation based view and the other is more of a logical / 
> namespace based view.  This proposal falls into the latter group (Brent's 
> pitch falls into the former).
> 
> Before I offer feedback on this proposal I'm wondering if you can provide 
> some solid examples of what benefits you see in the ability of a single file 
> to participate in more than one submodule.  

A single file defining more than one submodule is like a single file defining 
more than one data structure/extension.  If you decide that particular 
functionality deserves to reside in separate areas of concern, but don’t wish 
to break it out into separate files for whatever reason, just don’t.  Can you 
be more specific about the kind of thing you’re looking for?

> And also, what problems do you foresee if a file were restricted to being in 
> a single submodule (or at the top level of the module)?

The top level case is called out in the proposal.  We felt that requiring a 
top-level module declaration in every file to opt-in would be a needless 
complication to the semantics and would introduce an identifier-addressing 
problem.  Specifically, because modules aren’t namespaces we don’t have a way 
to refer to the “anonymous/global" top-level namespace as in C++ with a bare 
::, so this would become ambiguous without additional syntax

// Explicit declaration of top-level module Foo
module Foo {
  // Decls...
}

// Where does this constant live?  How can I address it from within Foo?
// Why isn’t it just a part of Foo?
let string = “Hello World!”

For one-file-per-module, that kind of restriction represents a particular way 
of organizing code and is a design pattern that is supported under this 
proposal.  We just happen to not enforce that particular pattern, and feel that 
it is the job of a linter to do so.  Really, this kind of restriction is to 
ease the mental burden on compiler writers who use it to build compilation unit 
dependency graphs.  Swift already considers all files when building its modules 
because you can extend any type (and now, any module) from any one of them so 
it doesn’t buy us anything other than an arbitrary restriction.

More generally, we need to move access control away as far away from 
filesystems as possible.  One day, the compiler is going to get ported over to 
a platform with some bonkers rules that are going to turn around and bite us.

~ Robert Widmann

> 
> Sent from my iPad
> 
> On Feb 20, 2017, at 7:56 PM, Robert Widmann via swift-evolution 
> > wrote:
> 
>> Good Evening All,
>> 
>> Jaden Geller and I have been considering a (sub)module system for Swift that 
>> would complement the existing language but also provide sorely needed 
>> modularity.  A draft of the proposal is attached to this email, but it can 
>> also be read as a gist 
>>  if you 
>> desire.
>> 
>> Cheers,
>> 
>> ~Robert Widmann
>> 
>> Modular Swift
>> 
>> Proposal: SE- 
>> Authors: Robert Widmann , Jaden Geller 
>> 
>> Review Manager: TBD
>> Status: Awaiting review
>>  
>> Introduction
>> 
>> Almost every major programming language supports some form of modular 
>> programming through constructs like (sub)modules, packages, or interfaces. 
>> Swift, though it provides top-level modules to organize code under, does not 
>> provide a complete implementation of any of these concepts, which has led 
>> instead to the proliferation of access control levels. This has not proven 
>> an effective way to decompose programs into manageable parts, and exposes 
>> the need for a real system of modules to solve this modularity problem once 
>> and for all.
>> 
>> Separation of code into distinct islands of functionality should be a 
>> first-class construct in the language, not dependent on external files and 
>> tools or filesystems. To that end, we propose the introduction of a 
>> lightweight module system for Swift.
>> 
>> Swift-evolution thread 
>>  
>> Motivation
>> 
>> Swift has reached a point in its evolution where rich libraries and large 
>> projects that take on many dependencies have matured significantly. To 
>> accomodate the information-hiding and semantics-signalling needs of these 
>> users at the time, Swift began its access control story with just three 
>> access modifiers: public, private, and internal then grew fileprivate and 
>> open as the need to express 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-20 Thread Jaden Geller via swift-evolution
Oh, you’re referring to the fact that a submodule under this proposal must be 
contained within braces? It would be purely additive to, in the future, 
annotate that the outer scope of a file is part of some given submodule.

Consider the following the following straw-man syntax that might be equivalent 
to `module Bar { func foo() { } }`:
```
module Bar follows // <- at top of file, indicating rest of file is submodule

func foo() { }
```

Does this address your question?

Thanks,
Jaden Geller

> On Feb 20, 2017, at 10:39 PM, Jonathan Hull  wrote:
> 
> 
>> On Feb 20, 2017, at 6:42 PM, Jaden Geller > > wrote:
>> 
>> Jon,
>> 
>> I think we might have miscommunicated. It is intended that outermost module 
>> is implicit; no `module` declaration is required to wrap every file. We 
>> tried to show this in the first code snippet.
>> 
>> What do you mean “covering only part of a file”?
> 
> I am assuming that the ModuleName { … }  only affects things within the 
> brackets.  Thus it is possible for only part of a file to be within a module. 
>  What are the benefits of allowing this, and are they worth the added 
> complexity?
> 
> Thanks,
> Jon
> 
> 
>> Cheers,
>> Jaden Geller
>> 
>>> On Feb 20, 2017, at 6:36 PM, Jonathan Hull via swift-evolution 
>>> > wrote:
>>> 
>>> What is the rational for having modules covering only part of a file?  
>>> Wouldn’t it be less clutter to have an annotation which worked for the 
>>> whole file.  At the very least it would be nice to have an option to spell 
>>> it in a way that applies to the whole file.  Otherwise, everything will be 
>>> indented another level.
>>> 
>>> I would honestly love to see something which just maps modules to 
>>> folders/groups for simplicity sake.
>>> 
>>> I haven’t thought about it too much yet, so I could easily be missing 
>>> something obvious...
>>> 
>>> Thanks,
>>> Jon
> 

___
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution


Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-20 Thread Robert Widmann via swift-evolution
The same benefits afforded by multiple extensions contained in the same file: 
sometimes you wish for your concerns not to overlap with one another, but feel 
that they do not necessarily warrant being split into separate files.  There 
really isn’t a reason we should enforce separation of submodules in the 
language if we can help it, it’s more the job of a linter.

~Robert Widmann

> On Feb 21, 2017, at 1:41 AM, Jonathan Hull  wrote:
> 
> I think my question is: Why do we want to allow submodules that are smaller 
> than a file?  What does that give us to offset the added complexity?
> 
> Thanks,
> Jon
> 
>> On Feb 20, 2017, at 6:44 PM, Robert Widmann > > wrote:
>> 
>> 
>>> On Feb 20, 2017, at 9:36 PM, Jonathan Hull >> > wrote:
>>> 
>>> What is the rational for having modules covering only part of a file?  
>>> Wouldn’t it be less clutter to have an annotation which worked for the 
>>> whole file.  At the very least it would be nice to have an option to spell 
>>> it in a way that applies to the whole file.  Otherwise, everything will be 
>>> indented another level.
>> 
>> That is a valid spelling (Rust, IIRC, allows that spelling), but one that is 
>> easy to miss sitting in a file and makes it confusing to introduce 
>> submodules.  If you include the annotation then define a submodule later 
>> down in the file, suddenly you have to remember whether you annotated the 
>> file or whether the submodule you’ve just written is going into the 
>> top-level module.  See:
>> 
>> // -module-name=Foo
>> // module Foo {
>> module Bar; // Shorthand for “This file defines Foo.Bar”
>> 
>> /* Code */
>> 
>> // This defines “Foo.Bar.Baz”, but would you know that if it appeared below 
>> the fold?
>> module Baz {}
>> //}
>> 
>> If anything, this can be added later if evolution converges on it.
>> 
>>> 
>>> I would honestly love to see something which just maps modules to 
>>> folders/groups for simplicity sake.
>>> 
>> 
>> There is nothing about this scheme that prevents you from organizing your 
>> code this way.  However, modulo that particular method of organization, you 
>> don’t really gain much as a user of the language by imposing this 
>> restriction.
>> 
>>> I haven’t thought about it too much yet, so I could easily be missing 
>>> something obvious...
>>> 
>>> Thanks,
>>> Jon
>>> 
>>> 
 On Feb 20, 2017, at 5:56 PM, Robert Widmann via swift-evolution 
 > wrote:
 
 Good Evening All,
 
 Jaden Geller and I have been considering a (sub)module system for Swift 
 that would complement the existing language but also provide sorely needed 
 modularity.  A draft of the proposal is attached to this email, but it can 
 also be read as a gist 
  if you 
 desire.
 
 Cheers,
 
 ~Robert Widmann
 
 Modular Swift
 
 Proposal: SE- 
 Authors: Robert Widmann , Jaden Geller 
 
 Review Manager: TBD
 Status: Awaiting review
  
 Introduction
 
 Almost every major programming language supports some form of modular 
 programming through constructs like (sub)modules, packages, or interfaces. 
 Swift, though it provides top-level modules to organize code under, does 
 not provide a complete implementation of any of these concepts, which has 
 led instead to the proliferation of access control levels. This has not 
 proven an effective way to decompose programs into manageable parts, and 
 exposes the need for a real system of modules to solve this modularity 
 problem once and for all.
 
 Separation of code into distinct islands of functionality should be a 
 first-class construct in the language, not dependent on external files and 
 tools or filesystems. To that end, we propose the introduction of a 
 lightweight module system for Swift.
 
 Swift-evolution thread 
 
  
 Motivation
 
 Swift has reached a point in its evolution where rich libraries and large 
 projects that take on many dependencies have matured significantly. To 
 accomodate the information-hiding and semantics-signalling needs of these 
 users at the time, Swift began its access control story with just three 
 access modifiers: public, private, and internal then grew fileprivate and 
 open as the need to express locality of implementation and 
 "subclassability" arose respectively. In doing so, Swift's access control 
 scheme has become anti-modular.
 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-20 Thread Jonathan Hull via swift-evolution
I think my question is: Why do we want to allow submodules that are smaller 
than a file?  What does that give us to offset the added complexity?

Thanks,
Jon

> On Feb 20, 2017, at 6:44 PM, Robert Widmann  wrote:
> 
> 
>> On Feb 20, 2017, at 9:36 PM, Jonathan Hull > > wrote:
>> 
>> What is the rational for having modules covering only part of a file?  
>> Wouldn’t it be less clutter to have an annotation which worked for the whole 
>> file.  At the very least it would be nice to have an option to spell it in a 
>> way that applies to the whole file.  Otherwise, everything will be indented 
>> another level.
> 
> That is a valid spelling (Rust, IIRC, allows that spelling), but one that is 
> easy to miss sitting in a file and makes it confusing to introduce 
> submodules.  If you include the annotation then define a submodule later down 
> in the file, suddenly you have to remember whether you annotated the file or 
> whether the submodule you’ve just written is going into the top-level module. 
>  See:
> 
> // -module-name=Foo
> // module Foo {
> module Bar; // Shorthand for “This file defines Foo.Bar”
> 
> /* Code */
> 
> // This defines “Foo.Bar.Baz”, but would you know that if it appeared below 
> the fold?
> module Baz {}
> //}
> 
> If anything, this can be added later if evolution converges on it.
> 
>> 
>> I would honestly love to see something which just maps modules to 
>> folders/groups for simplicity sake.
>> 
> 
> There is nothing about this scheme that prevents you from organizing your 
> code this way.  However, modulo that particular method of organization, you 
> don’t really gain much as a user of the language by imposing this restriction.
> 
>> I haven’t thought about it too much yet, so I could easily be missing 
>> something obvious...
>> 
>> Thanks,
>> Jon
>> 
>> 
>>> On Feb 20, 2017, at 5:56 PM, Robert Widmann via swift-evolution 
>>> > wrote:
>>> 
>>> Good Evening All,
>>> 
>>> Jaden Geller and I have been considering a (sub)module system for Swift 
>>> that would complement the existing language but also provide sorely needed 
>>> modularity.  A draft of the proposal is attached to this email, but it can 
>>> also be read as a gist 
>>>  if you 
>>> desire.
>>> 
>>> Cheers,
>>> 
>>> ~Robert Widmann
>>> 
>>> Modular Swift
>>> 
>>> Proposal: SE- 
>>> Authors: Robert Widmann , Jaden Geller 
>>> 
>>> Review Manager: TBD
>>> Status: Awaiting review
>>>  
>>> Introduction
>>> 
>>> Almost every major programming language supports some form of modular 
>>> programming through constructs like (sub)modules, packages, or interfaces. 
>>> Swift, though it provides top-level modules to organize code under, does 
>>> not provide a complete implementation of any of these concepts, which has 
>>> led instead to the proliferation of access control levels. This has not 
>>> proven an effective way to decompose programs into manageable parts, and 
>>> exposes the need for a real system of modules to solve this modularity 
>>> problem once and for all.
>>> 
>>> Separation of code into distinct islands of functionality should be a 
>>> first-class construct in the language, not dependent on external files and 
>>> tools or filesystems. To that end, we propose the introduction of a 
>>> lightweight module system for Swift.
>>> 
>>> Swift-evolution thread 
>>>  
>>> Motivation
>>> 
>>> Swift has reached a point in its evolution where rich libraries and large 
>>> projects that take on many dependencies have matured significantly. To 
>>> accomodate the information-hiding and semantics-signalling needs of these 
>>> users at the time, Swift began its access control story with just three 
>>> access modifiers: public, private, and internal then grew fileprivate and 
>>> open as the need to express locality of implementation and 
>>> "subclassability" arose respectively. In doing so, Swift's access control 
>>> scheme has become anti-modular.
>>> 
>>>  
>>> Proposed
>>>  solution
>>> 
>>> We propose the introduction of a lightweight module system for Swift. More 
>>> than simply namspaces, a module declaration interacts with Swift's access 
>>> control to provide an API boundary that allows better control over an 
>>> interface's design.
>>> 
>>>  
>>> Detailed
>>>  design
>>> 
>>>  
>>> Syntax
>>> 
>>> A module is a named 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-20 Thread Matthew Johnson via swift-evolution
Thanks for bringing up submodules Robert.  I agree it's a good time to discuss 
them.  

There seem to be two broad approaches to submodules.  One is more of a physical 
/ encapsulation based view and the other is more of a logical / namespace based 
view.  This proposal falls into the latter group (Brent's pitch falls into the 
former).

Before I offer feedback on this proposal I'm wondering if you can provide some 
solid examples of what benefits you see in the ability of a single file to 
participate in more than one submodule.  And also, what problems do you foresee 
if a file were restricted to being in a single submodule (or at the top level 
of the module)?

Sent from my iPad

> On Feb 20, 2017, at 7:56 PM, Robert Widmann via swift-evolution 
>  wrote:
> 
> Good Evening All,
> 
> Jaden Geller and I have been considering a (sub)module system for Swift that 
> would complement the existing language but also provide sorely needed 
> modularity.  A draft of the proposal is attached to this email, but it can 
> also be read as a gist if you desire.
> 
> Cheers,
> 
> ~Robert Widmann
> 
> Modular Swift
> Proposal: SE-
> Authors: Robert Widmann, Jaden Geller
> Review Manager: TBD
> Status: Awaiting review
> Introduction
> 
> Almost every major programming language supports some form of modular 
> programming through constructs like (sub)modules, packages, or interfaces. 
> Swift, though it provides top-level modules to organize code under, does not 
> provide a complete implementation of any of these concepts, which has led 
> instead to the proliferation of access control levels. This has not proven an 
> effective way to decompose programs into manageable parts, and exposes the 
> need for a real system of modules to solve this modularity problem once and 
> for all.
> 
> Separation of code into distinct islands of functionality should be a 
> first-class construct in the language, not dependent on external files and 
> tools or filesystems. To that end, we propose the introduction of a 
> lightweight module system for Swift.
> 
> Swift-evolution thread
> 
> Motivation
> 
> Swift has reached a point in its evolution where rich libraries and large 
> projects that take on many dependencies have matured significantly. To 
> accomodate the information-hiding and semantics-signalling needs of these 
> users at the time, Swift began its access control story with just three 
> access modifiers: public, private, and internal then grew fileprivate and 
> open as the need to express locality of implementation and "subclassability" 
> arose respectively. In doing so, Swift's access control scheme has become 
> anti-modular.
> 
> Proposed solution
> 
> We propose the introduction of a lightweight module system for Swift. More 
> than simply namspaces, a module declaration interacts with Swift's access 
> control to provide an API boundary that allows better control over an 
> interface's design.
> 
> Detailed design
> 
> Syntax
> 
> A module is a named region that introduces a lexical scope into which 
> declarations may be nested. The name of the module can be used to access 
> these member declarations. A module, like other aggregate structures in 
> Swift, may be extended with new declarations over one or more translation 
> units (files).
> 
> We propose a new declaration kind, module-decl be added to the language. A 
> proposed grammar using the new modulekeyword is given below:
> 
> GRAMMAR OF A MODULE DECLARATION
> 
> module-declaration -> `module` module-identifier module-body
> module-name -> identifier
> module-body -> { module-members(opt) }
> module-members -> module-member module-members(opt)
> module-member -> declaration | compiler-control-statement
> GRAMMAR OF A DECLARATION
> 
> + declaration -> module-declaration
> General Semantics
> 
> Syntax and semantics for imports, as it already supports referencing 
> submodules imported from C and Objective-C modules, remains unchanged:
> 
> // The outermost module is given explicitly 
> // by passing `-module-name=Foo` or exists implicitly, as today.
> // module Foo {
> public class A {}
> 
> module Bar {
>   module Baz {
> public class C {}
>   }
> 
>   public class B {}
> }
> 
> let message = "Hello, Wisconsin!"
> // } // End declarations added to module Foo.
> To consume this interface:
> 
> // imports all of Foo, Foo.Bar, and Foo.Bar.Baz
> import Foo.Bar.Baz
> 
> // imports Foo.A as A
> import class Foo.A
> // imports Foo.Bar.B as B
> import class Foo.Bar.B
> // imports Foo.Bar.Baz.C as C
> import class Foo.Bar.Baz.C
> A module declaration may only appear as a top-level entity or as a member of 
> another module declaration. The following code is therefore invalid:
> 
> module Foo {
>   class Bar {
> module Baz {} // error: module declaration cannot be nested inside type 
> 'Bar'
>   }
> }
> To extend an existing module declaration, simply reference its module name in 
> an extension declaration. 
> 
> // In 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-20 Thread Jaden Geller via swift-evolution
To further clarify—I think it would be accurate to say that this proposal 
introduces 2 things:

1) submodules, without changing the existing module system
2) `public` keyword for re-exporting modules

It is both unnecessary and not allowed to name the outermost module in the 
file. The `module` keyword simply introduces submodules. Notice that this works 
well with the notion of progress disclosure.

> On Feb 20, 2017, at 6:42 PM, Jaden Geller  wrote:
> 
> Jon,
> 
> I think we might have miscommunicated. It is intended that outermost module 
> is implicit; no `module` declaration is required to wrap every file. We tried 
> to show this in the first code snippet.
> 
> What do you mean “covering only part of a file”?
> 
> Cheers,
> Jaden Geller
> 
>> On Feb 20, 2017, at 6:36 PM, Jonathan Hull via swift-evolution 
>> > wrote:
>> 
>> What is the rational for having modules covering only part of a file?  
>> Wouldn’t it be less clutter to have an annotation which worked for the whole 
>> file.  At the very least it would be nice to have an option to spell it in a 
>> way that applies to the whole file.  Otherwise, everything will be indented 
>> another level.
>> 
>> I would honestly love to see something which just maps modules to 
>> folders/groups for simplicity sake.
>> 
>> I haven’t thought about it too much yet, so I could easily be missing 
>> something obvious...
>> 
>> Thanks,
>> Jon
>> 
>> 
>>> On Feb 20, 2017, at 5:56 PM, Robert Widmann via swift-evolution 
>>> > wrote:
>>> 
>>> Good Evening All,
>>> 
>>> Jaden Geller and I have been considering a (sub)module system for Swift 
>>> that would complement the existing language but also provide sorely needed 
>>> modularity.  A draft of the proposal is attached to this email, but it can 
>>> also be read as a gist 
>>>  if you 
>>> desire.
>>> 
>>> Cheers,
>>> 
>>> ~Robert Widmann
>>> 
>>> Modular Swift
>>> 
>>> Proposal: SE- 
>>> Authors: Robert Widmann , Jaden Geller 
>>> 
>>> Review Manager: TBD
>>> Status: Awaiting review
>>>  
>>> Introduction
>>> 
>>> Almost every major programming language supports some form of modular 
>>> programming through constructs like (sub)modules, packages, or interfaces. 
>>> Swift, though it provides top-level modules to organize code under, does 
>>> not provide a complete implementation of any of these concepts, which has 
>>> led instead to the proliferation of access control levels. This has not 
>>> proven an effective way to decompose programs into manageable parts, and 
>>> exposes the need for a real system of modules to solve this modularity 
>>> problem once and for all.
>>> 
>>> Separation of code into distinct islands of functionality should be a 
>>> first-class construct in the language, not dependent on external files and 
>>> tools or filesystems. To that end, we propose the introduction of a 
>>> lightweight module system for Swift.
>>> 
>>> Swift-evolution thread 
>>>  
>>> Motivation
>>> 
>>> Swift has reached a point in its evolution where rich libraries and large 
>>> projects that take on many dependencies have matured significantly. To 
>>> accomodate the information-hiding and semantics-signalling needs of these 
>>> users at the time, Swift began its access control story with just three 
>>> access modifiers: public, private, and internal then grew fileprivate and 
>>> open as the need to express locality of implementation and 
>>> "subclassability" arose respectively. In doing so, Swift's access control 
>>> scheme has become anti-modular.
>>> 
>>>  
>>> Proposed
>>>  solution
>>> 
>>> We propose the introduction of a lightweight module system for Swift. More 
>>> than simply namspaces, a module declaration interacts with Swift's access 
>>> control to provide an API boundary that allows better control over an 
>>> interface's design.
>>> 
>>>  
>>> Detailed
>>>  design
>>> 
>>>  
>>> Syntax
>>> 
>>> A module is a named region that introduces a lexical scope into which 
>>> declarations may be nested. The name of the module can be used to access 
>>> these member declarations. A module, like other aggregate structures in 
>>> Swift, may be extended with new declarations over one or more translation 
>>> units (files).
>>> 
>>> We propose a new declaration kind, module-decl be added to the 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-20 Thread Robert Widmann via swift-evolution

> On Feb 20, 2017, at 9:36 PM, Jonathan Hull  wrote:
> 
> What is the rational for having modules covering only part of a file?  
> Wouldn’t it be less clutter to have an annotation which worked for the whole 
> file.  At the very least it would be nice to have an option to spell it in a 
> way that applies to the whole file.  Otherwise, everything will be indented 
> another level.

That is a valid spelling (Rust, IIRC, allows that spelling), but one that is 
easy to miss sitting in a file and makes it confusing to introduce submodules.  
If you include the annotation then define a submodule later down in the file, 
suddenly you have to remember whether you annotated the file or whether the 
submodule you’ve just written is going into the top-level module.  See:

// -module-name=Foo
// module Foo {
module Bar; // Shorthand for “This file defines Foo.Bar”

/* Code */

// This defines “Foo.Bar.Baz”, but would you know that if it appeared below the 
fold?
module Baz {}
//}

If anything, this can be added later if evolution converges on it.

> 
> I would honestly love to see something which just maps modules to 
> folders/groups for simplicity sake.
> 

There is nothing about this scheme that prevents you from organizing your code 
this way.  However, modulo that particular method of organization, you don’t 
really gain much as a user of the language by imposing this restriction.

> I haven’t thought about it too much yet, so I could easily be missing 
> something obvious...
> 
> Thanks,
> Jon
> 
> 
>> On Feb 20, 2017, at 5:56 PM, Robert Widmann via swift-evolution 
>> > wrote:
>> 
>> Good Evening All,
>> 
>> Jaden Geller and I have been considering a (sub)module system for Swift that 
>> would complement the existing language but also provide sorely needed 
>> modularity.  A draft of the proposal is attached to this email, but it can 
>> also be read as a gist 
>>  if you 
>> desire.
>> 
>> Cheers,
>> 
>> ~Robert Widmann
>> 
>> Modular Swift
>> 
>> Proposal: SE- 
>> Authors: Robert Widmann , Jaden Geller 
>> 
>> Review Manager: TBD
>> Status: Awaiting review
>>  
>> Introduction
>> 
>> Almost every major programming language supports some form of modular 
>> programming through constructs like (sub)modules, packages, or interfaces. 
>> Swift, though it provides top-level modules to organize code under, does not 
>> provide a complete implementation of any of these concepts, which has led 
>> instead to the proliferation of access control levels. This has not proven 
>> an effective way to decompose programs into manageable parts, and exposes 
>> the need for a real system of modules to solve this modularity problem once 
>> and for all.
>> 
>> Separation of code into distinct islands of functionality should be a 
>> first-class construct in the language, not dependent on external files and 
>> tools or filesystems. To that end, we propose the introduction of a 
>> lightweight module system for Swift.
>> 
>> Swift-evolution thread 
>>  
>> Motivation
>> 
>> Swift has reached a point in its evolution where rich libraries and large 
>> projects that take on many dependencies have matured significantly. To 
>> accomodate the information-hiding and semantics-signalling needs of these 
>> users at the time, Swift began its access control story with just three 
>> access modifiers: public, private, and internal then grew fileprivate and 
>> open as the need to express locality of implementation and "subclassability" 
>> arose respectively. In doing so, Swift's access control scheme has become 
>> anti-modular.
>> 
>>  
>> Proposed
>>  solution
>> 
>> We propose the introduction of a lightweight module system for Swift. More 
>> than simply namspaces, a module declaration interacts with Swift's access 
>> control to provide an API boundary that allows better control over an 
>> interface's design.
>> 
>>  
>> Detailed
>>  design
>> 
>>  
>> Syntax
>> 
>> A module is a named region that introduces a lexical scope into which 
>> declarations may be nested. The name of the module can be used to access 
>> these member declarations. A module, like other aggregate structures in 
>> Swift, may be extended with new declarations over one or more translation 
>> units (files).
>> 
>> We propose a new declaration kind, module-decl be added to the language. A 
>> proposed grammar using the new 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-20 Thread Jaden Geller via swift-evolution
Jon,

I think we might have miscommunicated. It is intended that outermost module is 
implicit; no `module` declaration is required to wrap every file. We tried to 
show this in the first code snippet.

What do you mean “covering only part of a file”?

Cheers,
Jaden Geller

> On Feb 20, 2017, at 6:36 PM, Jonathan Hull via swift-evolution 
>  wrote:
> 
> What is the rational for having modules covering only part of a file?  
> Wouldn’t it be less clutter to have an annotation which worked for the whole 
> file.  At the very least it would be nice to have an option to spell it in a 
> way that applies to the whole file.  Otherwise, everything will be indented 
> another level.
> 
> I would honestly love to see something which just maps modules to 
> folders/groups for simplicity sake.
> 
> I haven’t thought about it too much yet, so I could easily be missing 
> something obvious...
> 
> Thanks,
> Jon
> 
> 
>> On Feb 20, 2017, at 5:56 PM, Robert Widmann via swift-evolution 
>> > wrote:
>> 
>> Good Evening All,
>> 
>> Jaden Geller and I have been considering a (sub)module system for Swift that 
>> would complement the existing language but also provide sorely needed 
>> modularity.  A draft of the proposal is attached to this email, but it can 
>> also be read as a gist 
>>  if you 
>> desire.
>> 
>> Cheers,
>> 
>> ~Robert Widmann
>> 
>> Modular Swift
>> 
>> Proposal: SE- 
>> Authors: Robert Widmann , Jaden Geller 
>> 
>> Review Manager: TBD
>> Status: Awaiting review
>>  
>> Introduction
>> 
>> Almost every major programming language supports some form of modular 
>> programming through constructs like (sub)modules, packages, or interfaces. 
>> Swift, though it provides top-level modules to organize code under, does not 
>> provide a complete implementation of any of these concepts, which has led 
>> instead to the proliferation of access control levels. This has not proven 
>> an effective way to decompose programs into manageable parts, and exposes 
>> the need for a real system of modules to solve this modularity problem once 
>> and for all.
>> 
>> Separation of code into distinct islands of functionality should be a 
>> first-class construct in the language, not dependent on external files and 
>> tools or filesystems. To that end, we propose the introduction of a 
>> lightweight module system for Swift.
>> 
>> Swift-evolution thread 
>>  
>> Motivation
>> 
>> Swift has reached a point in its evolution where rich libraries and large 
>> projects that take on many dependencies have matured significantly. To 
>> accomodate the information-hiding and semantics-signalling needs of these 
>> users at the time, Swift began its access control story with just three 
>> access modifiers: public, private, and internal then grew fileprivate and 
>> open as the need to express locality of implementation and "subclassability" 
>> arose respectively. In doing so, Swift's access control scheme has become 
>> anti-modular.
>> 
>>  
>> Proposed
>>  solution
>> 
>> We propose the introduction of a lightweight module system for Swift. More 
>> than simply namspaces, a module declaration interacts with Swift's access 
>> control to provide an API boundary that allows better control over an 
>> interface's design.
>> 
>>  
>> Detailed
>>  design
>> 
>>  
>> Syntax
>> 
>> A module is a named region that introduces a lexical scope into which 
>> declarations may be nested. The name of the module can be used to access 
>> these member declarations. A module, like other aggregate structures in 
>> Swift, may be extended with new declarations over one or more translation 
>> units (files).
>> 
>> We propose a new declaration kind, module-decl be added to the language. A 
>> proposed grammar using the new modulekeyword is given below:
>> 
>> GRAMMAR OF A MODULE DECLARATION
>> 
>> module-declaration -> `module` module-identifier module-body
>> module-name -> identifier
>> module-body -> { module-members(opt) }
>> module-members -> module-member module-members(opt)
>> module-member -> declaration | compiler-control-statement
>> GRAMMAR OF A DECLARATION
>> 
>> + declaration -> module-declaration
>>  
>> General
>>  Semantics
>> 
>> Syntax and semantics for imports, as it already supports referencing 
>> 

Re: [swift-evolution] [Proposal][Discussion] Modular Swift

2017-02-20 Thread Jonathan Hull via swift-evolution
What is the rational for having modules covering only part of a file?  Wouldn’t 
it be less clutter to have an annotation which worked for the whole file.  At 
the very least it would be nice to have an option to spell it in a way that 
applies to the whole file.  Otherwise, everything will be indented another 
level.

I would honestly love to see something which just maps modules to 
folders/groups for simplicity sake.

I haven’t thought about it too much yet, so I could easily be missing something 
obvious...

Thanks,
Jon


> On Feb 20, 2017, at 5:56 PM, Robert Widmann via swift-evolution 
>  wrote:
> 
> Good Evening All,
> 
> Jaden Geller and I have been considering a (sub)module system for Swift that 
> would complement the existing language but also provide sorely needed 
> modularity.  A draft of the proposal is attached to this email, but it can 
> also be read as a gist 
>  if you 
> desire.
> 
> Cheers,
> 
> ~Robert Widmann
> 
> Modular Swift
> 
> Proposal: SE- 
> Authors: Robert Widmann , Jaden Geller 
> 
> Review Manager: TBD
> Status: Awaiting review
>  
> Introduction
> 
> Almost every major programming language supports some form of modular 
> programming through constructs like (sub)modules, packages, or interfaces. 
> Swift, though it provides top-level modules to organize code under, does not 
> provide a complete implementation of any of these concepts, which has led 
> instead to the proliferation of access control levels. This has not proven an 
> effective way to decompose programs into manageable parts, and exposes the 
> need for a real system of modules to solve this modularity problem once and 
> for all.
> 
> Separation of code into distinct islands of functionality should be a 
> first-class construct in the language, not dependent on external files and 
> tools or filesystems. To that end, we propose the introduction of a 
> lightweight module system for Swift.
> 
> Swift-evolution thread 
>  
> Motivation
> 
> Swift has reached a point in its evolution where rich libraries and large 
> projects that take on many dependencies have matured significantly. To 
> accomodate the information-hiding and semantics-signalling needs of these 
> users at the time, Swift began its access control story with just three 
> access modifiers: public, private, and internal then grew fileprivate and 
> open as the need to express locality of implementation and "subclassability" 
> arose respectively. In doing so, Swift's access control scheme has become 
> anti-modular.
> 
>  
> Proposed
>  solution
> 
> We propose the introduction of a lightweight module system for Swift. More 
> than simply namspaces, a module declaration interacts with Swift's access 
> control to provide an API boundary that allows better control over an 
> interface's design.
> 
>  
> Detailed
>  design
> 
>  
> Syntax
> 
> A module is a named region that introduces a lexical scope into which 
> declarations may be nested. The name of the module can be used to access 
> these member declarations. A module, like other aggregate structures in 
> Swift, may be extended with new declarations over one or more translation 
> units (files).
> 
> We propose a new declaration kind, module-decl be added to the language. A 
> proposed grammar using the new modulekeyword is given below:
> 
> GRAMMAR OF A MODULE DECLARATION
> 
> module-declaration -> `module` module-identifier module-body
> module-name -> identifier
> module-body -> { module-members(opt) }
> module-members -> module-member module-members(opt)
> module-member -> declaration | compiler-control-statement
> GRAMMAR OF A DECLARATION
> 
> + declaration -> module-declaration
>  
> General
>  Semantics
> 
> Syntax and semantics for imports, as it already supports referencing 
> submodules imported from C and Objective-C modules, remains unchanged:
> 
> // The outermost module is given explicitly 
> // by passing `-module-name=Foo` or exists implicitly, as today.
> // module Foo {
> public class A {}
> 
> module Bar {
>   module Baz {
> public class C {}
>   }
> 
>   public class B {}
> }
> 
> let message = "Hello, Wisconsin!"
> // } // End declarations added to module Foo.
> To consume this interface:
> 
> // imports all of Foo, Foo.Bar, and Foo.Bar.Baz
> import Foo.Bar.Baz
> 
> // imports Foo.A as A
> import