[swift-evolution] [Pitch] Let's talk about submodules

Matthew Johnson matthew at anandabits.com
Wed Feb 22 09:16:27 CST 2017


> On Feb 22, 2017, at 1:31 AM, Brent Royal-Gordon <brent at architechies.com> wrote:
> 
>> On Feb 21, 2017, at 8:33 PM, Matthew Johnson <matthew at anandabits.com> wrote:
>> 
>>> A submodule may not import any direct parent module (parent, grandparent, etc.), but may import any other submodule in the same module. This list shows permitted imports for a project with four modules/submodules:
>>> 
>>> 	ModKit
>>> 		- ModKit.Foo
>>> 		- ModKit.Foo.Bar
>>> 		- ModKit.Quux
>>> 	ModKit.Foo
>>> 		- ModKit.Foo.Bar
>>> 		- ModKit.Quux
>>> 	ModKit.Foo.Bar
>>> 		- ModKit.Quux
>>> 	ModKit.Quux
>>> 		- ModKit.Foo
>>> 		- ModKit.Foo.Bar
>> 
>> Am I understanding this correctly?  It looks like ModKit.Foo.Bar cannot see or import any symbols declared in ModKit.Foo or ModKit.  Is that correct?  Descendents cannot see or import symbols declared in ancestors (including public symbols) but they can import any submodule that is not their ancestor (and therefore see public symbols in any submodule that’s not an ancestor by way of importing that submodule)?  
> 
> Yes, that's correct.
> 
>> I think I understand why you might have specified this design but am interested in hearing you elaborate a bit further on the rationale.
> 
> A few reasons:
> 
> 1. It creates a stricter layering between parent modules and submodules: submodules are for lower layers, while parent modules are for higher layers. Layering reduces spaghetti, and less spaghetti is generally a good thing.
> 
> 2. It limits the amount of code the compiler has to consider at once.
> 
> 3. It helps avoid (but doesn't completely prevent) circular dependencies between submodules, ensuring there's an order in which they can be compiled separately.

These are the reasons I suspected.  Glad we’re on the same page.

> 
> On the other hand, a design which considered all submodules at once would certainly be more flexible. You could call back and forth between submodules and their parents freely, and organize your code more flexibly. But I'm not sure it can be made to work with this "build system decides what's in a submodule" approach—I'm trying to imagine how you would tell the compiler about the submodule mappings for fifty files without that information being in the source code, and I'm not liking any of the solutions I'm coming up with.

Yes, this requirement does seem to be implied by the build system approach you suggested.  For the sake of discussion, would you still desire these rules if the files in a submodule was determined with a mechanism that allowed for this flexibility.  Let’s say for discussion even circular dependencies were possible to implement.  What rules would you consider valuable enough to limit flexibility of code organization?  I’m not arguing for maximum flexibility at all (I don’t think that would be the right design).  But I am interested in whether you would change the rules without the limitation of the build system mechanism or not.

> 
> -- 
> Brent Royal-Gordon
> Architechies
> 



More information about the swift-evolution mailing list