Quick Tip

How to make sure your CI pipelines are always up to date?

Published on: March 12, 2024

When you work with CI, you’ll know how frustrating it can be when a CI server has versions of Xcode or other tools installed than the tools that you’re using. Especially major Xcode releases can be problematic. If your CI doesn’t have the same new versions available while your project uses recently released features which will lead your builds to fail. An obvious example of this would be when you start using features that are exclusive to the latest iOS version. If Xcode doesn’t know about these features then your project won’t build. An out of date CI can cause...

Read more...

SwiftUI’s Bindable property wrapper explained

Published on: June 30, 2023

WIth the introduction of Xcode 15 beta and its corresponding beta OSses (I would say iOS 17 beta, but of course we also get macOS, iPadOS, and other betas...) Apple has introduced new state mangement tools for SwiftUI. One of these new tools is the @Bindable property wrapper. In an earlier post I explained that @Binding and @Bindable do not solve the same problem, and that they will co-exist in your applications. In this post, I would like to clarify the purpose and the use cases for @Bindable a little bit better so that you can make better decisions when...

Read more...

What’s the difference between Macros and property wrappers?

Published on: June 6, 2023

With Swift 5.9 and Xcode 15, we have the ability to leverage Macros in Swift. Macros can either be written with at @ prefix or with a # prefix, depending on where they're being used. If you want to see some examples of Macros in Swift, you can take a look at this repository that sheds some light on both usage and structure of Macros. When we look at Macros in action, they can look a lot like property wrappers: @CustomCodable struct CustomCodableString: Codable { @CodableKey(name: "OtherName") var propertyWithOtherName: String var propertyWithSameName: Bool func randomFunction() { } } The example...

Read more...

Setting up a simple local web socket server

Published on: January 24, 2023

Every once in a while I find myself writing about or experimenting with web sockets. As an iOS developer, I’m not terribly familiar with setting up and programming servers that leverage web sockets beyond some toy projects in college. Regardless, I figured that since I have some posts that cover web sockets on my blog, I should show you how I set up the socket servers that I use in those posts. Before you read on, I’m going to need you to promise me you won’t take the code I’m about to show you to a production environment… You promise?...

Read more...

Debugging Network Traffic With Proxyman

Published on: May 12, 2022

Disclaimer: This post is not sponsored by Proxyman, nor am I affiliated with Proxyman in any way. I pay for my license myself, and this post is simply written as a guide to learning more about a tool that I find very important in the iOS Developer toolbox. Networking is an essential part of modern iOS applications. Most apps I’ve worked have some kind of networking component. Sometimes the networking layer involves user authentication, token refresh flows, and more. Other times, I’ll simply need to hit one or two endpoints to fetch new data or configuration files for my app....

Read more...

What is the “any” keyword in Swift?

Published on: March 15, 2022

This article has been updated for Swift 5.7 With Swift 5.6, Apple added a new keyword to the Swift language: any. As you'll see in this post, usage of the any keyword looks very similar to how you use the some keyword. They're both used in front of protocol names, and they both tell us something about how that protocol is used. Once you dig deeper into what any means, you'll find that it's very different from some. In fact, you might come to the conclusion that any is somewhat of the opposite of some. In this post, you will...

Read more...

Adding custom keys to the SwiftUI environment

Published on: January 10, 2022

Sometimes you’ll find yourself in a situation where you want to conveniently pass some object down via the SwiftUI environment. An easy way to do this is through the .environmentObject view modifier. The one downside of this view modifier and corresponding @EnvironmentObject property wrapper is that the object you add to the environment must be an observable object. Luckily, we can extend the SwiftUI environment to add our own objects to the @Environment property wrapper without the need to make these objects observable. For example, your app might have to do some date formatting, and maybe you’re looking for a...

Read more...

Forcing an app out of memory on iOS

Published on: December 23, 2021

I’ve recently been working on a background uploading feature for an app. One of the key aspects to get right with a feature like that is to correctly handle scenarios where your app is suspended by the system due to RAM constraints or other, similar, reasons. Testing this is easily done by clearing the RAM memory on your device. Unfortunately, this isn’t straightforward. But it’s also not impossible. Note that opening the task switcher and force closing your app from there is not quite the same as forcing your app to be suspended. Or rather, it’s not the same as...

Read more...

An extensive guide to sorting Arrays in Swift

Published on: April 7, 2021

When you're working with Arrays in Swift, it's likely that you'll want to sort them at some point. In Swift, there are two ways to sort an Array: Through the Comparable implementation for each element in your array By providing a closure to perform a manual/specialized comparison between elements If you have a homogenous array of elements, for example [String], you can rely on String's implementation of Comparable to sort an array of String in some sensible manner. There are two ways to sort an array of Comparable elements: var strings = ["Oh", "Hello", "World", "This", "Is", "An", "Unsorted", "Array"]...

Read more...

What does “atomic” mean in programming?

Published on: January 6, 2021

When you're learning about databases or multithreaded programming, it's likely that you'll come across the term "atomic" at some point. Usually you'll hear the term in the context of an operation. For example, an atomic read / write operation. Or atomic access to a property. But what does this mean? Generally, you can summarize atomic as "one at a time". For example, when accessing or mutating a property is atomic, it means that only one read or write operation can be performed at a time. If you have a program that reads a property atomically, this means that the property...

Read more...