[swift-evolution] Simplifying Access Using 'Hidden'

Matthew Johnson matthew at anandabits.com
Wed Feb 15 09:52:30 CST 2017


> On Feb 15, 2017, at 9:37 AM, Michel Fortin via swift-evolution <swift-evolution at swift.org> wrote:
> 
> 
>> Le 15 févr. 2017 à 9:28, Vladimir.S via swift-evolution <swift-evolution at swift.org> a écrit :
>> 
>> On 15.02.2017 14:29, Joanna Carter via swift-evolution wrote:
>>>> The beauty of Swift 2's access modifiers was that they were based
>>>> around files and modules, explicitly rejecting types and scopes as
>>>> units for determining visibility. It seems at base there's a group of
>>>> people who reject that decision altogether. Hence, new `private`,
>>>> proposals around `protected`, `friend`, `hidden`, `extensible`, etc.
>>> 
>>> I suppose, for those coming from an Objective-C only background, any
>>> extra visibilities are seen as a bonus.
>>> 
>>> For those coming from a Pascal background, file-based visibility seems
>>> more natural.
>>> 
>>> But for those of us who have used languages like C++ and C#, losing the
>>> visibilities that we have been used to can seriously affect how we think
>>> and design stuff.
>>> 
>> 
>> Was surprised that you expressed exactly what I'm thinking about this subject.
>> 
>> I do believe even in Swift we need a way to say "only code that *knows* what it does should see this" and to not force us to write(and manage) the the code in same file.
>> Yes, some implementation details that shouldn't be used by "users" of the type, but can be used by "extenders" of our type. At least in the same module.
>> 
>> While reading, the question was raised(if was discussed, let me know pls): what if we extend the meaning of 'private' to 'visible to current type/scope and subtypes and extensions in the *same module*' ?
>> This will help us to split types by files, help to better model access policy for fields/methods(i.e. only scope that can know about details can see them) while 'private' still will be hidden outside of the module even for subclasses/extensions.
>> 
>> So, we'll have such situation:
>> 
>> "modifier" -> "can be accessed from"
>> -------------------------------
>> public -> outside of the mondule
>> internal -> inside the module only
>> fileprivate -> the same file only
>> private -> the same type/scope, or subtype, or extension in the same module. I.e. some kind of 'internal' but scope-oriented.
>> 
>> Actually I still believe we need current 'private' and additionally some 'protected' with meaning "access from subtype, or extension" probably with this limitation: "only in the same module". But suggested extended 'private' will be also OK for me.
>> 
>> Thoughts?
> 
> Here's an idea in three points:
> 
> 1. Return to the Swift 2 definition of `private`.
> 2. Introduce `scoped` to limit the visibility to within the same type, subtype, or extension.
> 3. Allow mixing the two.
> 
> So you have:
> 
> 	private         // current file
> 	private scoped  // current file, in the same type, subtype, or ext.
> 	internal        // current module
> 	internal scoped // current module, in the same type, subtype, or ext.
> 	public          // external modules
> 	public scoped   // maybe we want that one?
> 
> Since `internal` is implied, using `scoped` alone would be equivalent to `internal scoped`.
> 
> Swift 3's private could be mapped to `private scoped` to achieve (almost) the same results and thus preserve source compatibility.

This definition of `scoped` is actually much different than the current `private` which restricts visibility to the *current* scope.  Your definition allows visibility in an unlimited number of scopes that just happen to be of the same type.  I don’t think `scoped` is a good name for this.  

`private(type)` would be a better name if we were going to make this a modification of the existing access modifiers.  However, I don’t think this is the right direction.  If we’re going to have an access modifier that means “in the same file *and* the same type” I think that should simply be called `private` (a “soft default”).  If we’re going to have something between `internal` and `fileprivate` I think it would be better to explore submodules than introduce something like `internal(type)`.

> 
> -- 
> Michel Fortin
> https://michelf.ca
> 
> _______________________________________________
> swift-evolution mailing list
> swift-evolution at swift.org
> https://lists.swift.org/mailman/listinfo/swift-evolution



More information about the swift-evolution mailing list