Coding Explorer Blog

Exploring how to code for iOS in Swift and Objective-C

  • Home
  • Apps
  • About
  • Contact

Access Control in Swift

Xcode 11.6 Swift 5.2.4

Last updated on August 10, 2020

The access control in Swift is much more like the access control I am accustomed to in other languages like C# or Java, and I am quite thankful for that.  I’m not saying there is anything wrong with Objective-C’s way of doing it, while it was different, I did like having the private properties in the interface block of the implementation (.m) file, and the public properties and methods in the header (.h) file.  It made it easy to know exactly where to look.

Nonetheless, access control is here in Swift, so here we go.  You can set access control to many things in Swift, particularly properties and methods, but you can even set it to types, initializers, subscripts, or protocols.  Swift currently has three levels of access control:

  • Public
  • Internal
  • Fileprivate
  • Private

The section in Apple’s iBook The Swift Programming Language, described the major differences between them in a few paragraphs, when writing this, I kept having to look back to remember the specific aspects of where they were all visible.  So, I thought it would be better to show the major differences in tabular form…. behold:

 

Visible to… Defining Scope Defining Source Defining Module

Source that Imports

Defining Module

Public ✓ ✓ ✓ ✓
Internal ✓ ✓ ✓
Fileprivate ✓ ✓
Private ✓

Now, we haven’t talked about Module’s yet on this blog, but basically, this is Swift’s name for “namespaces” in other languages.  They are also part of how Apple makes headers unnecessary in Swift.  Effectively, a module is basically the target you are building for.  For most of us, that means “your app,” but it could also be a framework instead.

Let’s look a little more in depth into these access control levels.

Swift Access Controls

Public

As expected, public is the most visible access control level you can have.  It allows the user to use that property, function, etc in the defining source, the module that source is in, and anything that imports that module.  Basically, it can be seen anywhere.  This is particularly important for frameworks.  This is what will give your framework a public API, to be called by whatever imports your framework.

Internal

This is the default access level.  It can be seen in the defining source, as well as the module that source is in, but it cannot be seen by something that imports that module.  If used in a framework, it lets other parts of your module see these aspects, but not something that imports your module.  In Objective-C, it would basically be equivalent to having them declared in your header file.

Fileprivate

Fileprivate can only be seen in the defining source.  This hides the implementation details of that source file, so that the rest of your module does not have access to parts that have little meaning outside of the context of the original source file.  In Objective-C, it would be equivalent to being declared in the interface part of your implementation file.

Private

This is the least visible access control level.  Private can only be seen in the defining scope.  So if you made an extension of your class in the same source file, but wanted a function only visible in that extension and not in the main class, you would declare it private.

The @testable Attribute

Since the release of Swift 2, these issues have been mitigated with the addition of the ” @testable ” import attribute.  It basically treats anything that is marked as “internal” as if it were public, to the code that imports using that attribute.  So to test with your internal methods, properties, types, etc., in your unit test class, just “@testable” before the import of whichever module you are testing.

Using Access Controls

With all this talk about access controls, I should probably show how they are used?  Well, they are really simple, you basically just begin your declaration of a variable or class with the access modifier you want, so:

public class myPublicTranslator { }

public func translateSomeText(inputText: String) -> String { }

fileprivate let implementationDetail = "A Secret"

private let superSecretImplementationDetail = "A SUPER Secret"

Nothing too special there.

Limitations to Access Controls

There are a few limitations to access controls, and most of them are just to enforce common sense.  For instance, a public variable cannot have an internal or private type.  That seems pretty obvious.  If the type was private, how could anything that can only read the public variable have access to it?

Another similarly obvious one, a function can have an access level no more visible than the least visible type in its parameters or return value.  You can make a private type that contains public and internal types as parameter or return types.  However, you cannot make a public function that uses internal parameter or return types.  Similar reasoning, since nothing from another module that can only read public items could possibly have access to internal or private types.

Conclusion

Access controls are definitely a welcome addition to Swift.  They will make it much easier to enforce interfaces between your source files and modules, as opposed to just leaving your implementation details out for all to see.

I hope you found this article helpful.  If you did, please don’t hesitate to share this post on Twitter or your social media of choice, every share helps.  Of course, if you have any questions, don’t hesitate to contact me on the Contact Page, or on Twitter @CodingExplorer, and I’ll see what I can do.  Thanks!

Sources

  • The Swift Programming Language – Apple Inc.

Filed Under: Swift Tagged With: Access Controls

Subscribe to the Coding Explorer Newsletter

* indicates required

Follow Us

Facebooktwitterrss

Recent Posts

  • Error Handling in Swift
  • Creating and Modifying a URL in your Swift App
  • Watch Connectivity in Swift — Application Context
  • watchOS Hello World App in Swift
  • API Availability Checking in Swift

Categories

  • Class Reference
  • General
  • Interface Builder
  • My Apps
  • Objective-C
  • Swift
  • Syntax
  • Tutorial
  • Uncategorized

Archives

  • May 2016
  • March 2016
  • February 2016
  • December 2015
  • July 2015
  • June 2015
  • April 2015
  • February 2015
  • January 2015
  • December 2014
  • November 2014
  • October 2014
  • September 2014
  • August 2014
  • July 2014
  • June 2014
  • May 2014
  • April 2014
  • March 2014
  • January 2014
  • November 2013
  • September 2013
  • August 2013
  • July 2013
  • Terms Of Use
  • Privacy Policy
  • Affiliate Disclaimer

Subscribe to the Coding Explorer Newsletter

* indicates required

Copyright © 2025 Wayne Media LLC · Powered by Genesis Framework · WordPress