In Swift, access levels (private, fileprivate, internal, public, open) apply not only to classes, structures, and their properties but also to nested types. A nested type by default inherits the access level of its enclosing type unless a different explicit restriction is specified.
Key nuances:
internal, the nested type cannot have a more open access level than the outer type but can be more 'closed' (for example, outer — public, nested — private).internal will not be visible from other modules.Example:
public class A { public struct B { fileprivate func foo() {} } }
In this example, both A and B are public, but the method foo() is file-private.
Question: "Can a nested type have a higher access level than its enclosing type?"
Answer: No, the access level of a nested type cannot exceed the access level of its enclosing type. If you attempt to declare a nested type with a higher access level, the compiler will produce an error.
Example of an error:
internal struct MyStruct { public enum MyEnum { ... } // Error: public cannot be inside internal }
Story 1
In a general framework, the access levels of nested structures were not synchronized with external types. In the release version, this led to the inability to use internal enums in the client application, requiring an urgent interface change.
Story 2
In a large project, an internal service object had a nested class with statuses declared as internal. After the addition of a new module that depended on this class, integration became impossible without raising the access level and fully recompiling the SDK.
Story 3
In a complex library, some nested structures were declared as public, while the container itself was internal. During the migration to a new version, critical errors arose: public types did not compile in an external context, which delayed updates across multiple teams.