You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Copy file name to clipboardExpand all lines: proposals/0025-scoped-access-level.md
+12-10Lines changed: 12 additions & 10 deletions
Original file line number
Diff line number
Diff line change
@@ -7,28 +7,29 @@
7
7
8
8
## Introduction
9
9
10
-
Scoped access level allows to hide implementation details of a class or a class extension at the class / class extension level instead of a file. It’s concise expression of the intent that a particular part of a class or extension definition is there only to implement a public API for other classes or extensions and must not be used directly anywhere outside of the scope of the class or the extension.
10
+
Scoped access level allows to hide implementation details of a class or a class extension at the class/extension level, instead of a file. It is a concise expression of the intent that a particular part of a class or extension definition is there only to implement a public API for other classes or extensions, and must not be used directly anywhere outside of the scope of the class or the extension.
11
11
12
12
## Motivation
13
13
14
14
Currently, the only reliable way to hide implementations details of a class is to put the code in a separate file and mark it as private. This is not ideal for the following reasons:
15
15
16
-
-it’s not clear whether the implementation details are meant to be completely hidden or can be shared with some related code without the danger of misusing the APIs marked as private. If a file already has multiple classes, it’s not clear if a particular API is meant to be hidden completely or can be shared with the other classes.
16
+
-It is not clear whether the implementation details are meant to be completely hidden or can be shared with some related code without the danger of misusing the APIs marked as private. If a file already has multiple classes, it is not clear if a particular API is meant to be hidden completely or can be shared with the other classes.
17
17
18
-
-it forces one class per file structure, which is very limiting. Putting related APIs and / or related implementations helps ensure consistency and reduces the time to find a particular API or implementation. This does not mean that the classes in the same file need to share otherwise hidden APIs, but there is no way to express it with the current access levels.
18
+
-It forces a one class per file structure, which is very limiting. Putting related APIs and/or related implementations in the same file helps ensure consistency and reduces the time to find a particular API or implementation. This does not mean that the classes in the same file need to share otherwise hidden APIs, but there is no way to express it with the current access levels.
19
19
20
-
Another, less reliable way, is to prefix APIs that are meant to be hidden with a _ or do something similar. That works, but it’s not enforced by the compiler, and those APIs show up in tools like code completion, so the programmer has to filter out the noise. Also, there is a greater danger of using private APIs if they do something similar to public APIs but are somehow more optimized (because they make additional assumptions about the internal state).
20
+
Another, less reliable, way is to prefix APIs that are meant to be hidden with a `_` or do something similar. That works, but it’s not enforced by the compiler, and those APIs show up in tools like code completion, so the programmer has to filter out the noise - although these tools could quite easily support hiding methods with the `_` prefix standard. Also, there is a greater danger of using private APIs if they do something similar to public APIs but are somehow more optimized (because they make additional assumptions about the internal state).
21
21
22
-
The existing solutions are in some ways similar to solutions for untyped collections. It is usually possible to give collection a name that would imply the type of elements it holds (similar to using _ to indicate private), but it is not the same as specifying it explicitly. Just as with generics, the intent not to share the implementation details with any other class is much clearer with support from the language as opposed to where the code is in the project. Also, with untyped collections, it is possible to add an element of a different type (deliberately or not). Generics make it impossible, and it’s enforced by the compiler. Similarly, a dedicated access level modifier could enforce hiding implementation details at the compiler level and make it impossible to accidentally misuse or (deliberately use) implementation details in a context that the class meant not to share.
22
+
The existing solutions are in some ways similar to those for untyped collections. It is usually possible to give collection a name that would imply the type of elements it holds (similar to using _ to indicate private), but it is not the same as specifying it explicitly. Just as with generics, the intent not to share the implementation details with any other class is much clearer with support from the language as opposed to where the code is in the project. Also, with untyped collections, it is possible to add an element of a different type (deliberately or not). Generics make it impossible, and it’s enforced by the compiler. Similarly, a dedicated access level modifier could enforce hiding implementation details at the compiler level and make it impossible to accidentally misuse or (deliberately use) implementation details in a context that the class meant not to share.
23
23
24
24
## Proposed solution
25
25
26
-
Add another access level modifier that is meant to express that the API is visible only within the scope in which it is defined. Properties, functions, and nested types marked this way would be completely hidden outside the class or class extension definition.
26
+
Add another access level modifier that is meant to express that the API is visible only within the scope in which it is defined. Properties, functions, and nested types marked this way would be completely hidden outside the class or class extension definition.
27
27
28
28
## Detailed design
29
29
30
30
When a function or a property is defined with a scoped access modifier, it is visible only within that lexical scope. For example:
31
31
32
+
```swift
32
33
classA {
33
34
local var counter =0
34
35
@@ -49,17 +50,18 @@ extension A {
49
50
// hidden from anywhere else, so incrementTwice() doesn’t show up in
50
51
// code completion outside of this extension
51
52
local funcincrementTwice() {
52
-
advanceCount()
53
-
advanceCount()
53
+
incrementCount()
54
+
incrementCount()
54
55
}
55
56
}
57
+
```
56
58
57
59
## Impact on existing code
58
60
59
61
The existing code is completely unaffected.
60
62
61
63
## Alternatives considered
62
64
63
-
1) do nothing and use _ and / or split the code into more files and use the private modifier. The proposed solution makes the intent much clearer, it would be enforced by the compiler, and the language does not dictate how the code must be organized.
65
+
1. Do nothing and use `_` and `/` or split the code into more files and use the private modifier. The proposed solution makes the intent much clearer, it would be enforced by the compiler, and the language does not dictate how the code must be organized.
64
66
65
-
2) introduce a scoped namespace that would make it possible to hide APIs in part of the file. This introduces an extra level of grouping and nesting and forces APIs to be grouped by access level instead of a logical way that may make more sense.
67
+
2. Introduce a scoped namespace that would make it possible to hide APIs in part of the file. This introduces an extra level of grouping and nesting and forces APIs to be grouped by access level instead of a logical way that may make more sense.
0 commit comments