Categories
iOS

How to fix missing dSYM files on Firebase Crashlytics

So you decided to set up Firebase Crashlytics on your iOS app to be able to track any crashes that may occur, either while testing or in production. You followed the Firebase documentation step by step and did everything correctly. You forced a crash and it appeared on the Firebase console? Great.

You uploaded the app on TestFlight and told your testers to start testing. After some time, you open the Firebase console and notice that there were no crashes recorded and you see a big red sign telling you that you have to upload dSYM files to be able to process those crashes.

But how are you going to do that?

Let’s first explain what a dSYM file is.

Firstly, when Xcode compiles source code to machine code it generates a list of symbols (class names, global variables, method, and function names). That symbol and the information about the file name and the line number where the symbol is declared constitute a debug symbol. Those debug symbols are used both by the Xcode debugger and for generating the crash reports. When you create a debug build these debug symbols are contained inside the compiled binary file.

Archiving an app

When you create a release build (when you archive an app) debug symbols are placed in a dSYM (Debug Symbol) file to reduce the size of the app. Each binary file (main app executable, frameworks, and app extensions) in an app contains its dSYM file. The binary file and its corresponding dSYM file are tied together by a build UUID. This build UUID is unique, even when the same source code gets compiled with a different Xcode version or build settings, a different UUID will get generated. dSYM files are not the only symbol files. When you archive an app with bitcode, the symbols in the dSYM files are replaced by obfuscated symbols to provide privacy for symbol names. A new symbol file bcsymbolmap (bitcode symbol map) gets created and its purpose is to translate these hidden symbol names back to the original symbol names.

Uploading app to the app store

When you upload an app to the app store it is uploaded as a bitcode. Bitcode is an intermediate representation of how the code looks. That bitcode is later converted to an app binary by Apple. Those new binaries now have different UUIDs than dSYMs that were uploaded to Firebase during build time. So new dSYM files get created and we have to manually upload them to Firebase.

How to fix

1. Open Firebase Console and see for what build should you upload the dSYM files

2. Open that build on App Store Connect 

3. Open build metadata, under General Information find the Includes Symbols tab and click on Download dSYM

4. Unzip the downloaded file

5. Write down the paths for the Pods folder of your application, GoogleService-Info.plst file, and the downloaded dSYMs folder

6. Open the terminal and execute the following command

/path/to/pods/directory/FirebaseCrashlytics/upload-symbols-gsp /path/to/GoogleService-Info.plist -p ios /path/to/dSYMs

7.  If you’ve written the command correctly there should be no warnings and errors and the console should output UUIDs of all the dSYM files that have been uploaded. You can check if they match with the ones in your Firebase console.

8. Wait a couple of minutes for Firebase to process the files

And voila, all the crashes should be displayed on the console.

These are the sources I used in the making of this tutorial, hope you found it useful:

https://developer.apple.com/documentation/xcode/building_your_app_to_include_debugging_information

https://www.tutorialspoint.com/what-is-embedded-bitcode-and-what-does-enable-bitcode-do-in-xcode

https://stackoverflow.com/questions/34363485/why-does-recompiling-from-bitcode-make-me-unable-to-symbolicate-in-xcode-ad-hoc

https://stackoverflow.com/questions/54577202/how-to-run-upload-symbols-to-upload-dsyms-as-a-part-of-xcode-build-process

Until the next read, stay well and safe.

Categories
iOS

How to create a QR code widget

Yes, the long-awaited widgets for iOS devices are finally here!

After the big announcement made at Worldwide Developers Conference in June 2020, Apple has released its biggest update regarding the iOS operating system in September 2020 – iOS 14, with the amazing feature that allows its users to create and add widgets to the home screen of their device.

Hoping that we are not joining the party too late, we decided to try it out ourselves and share our thoughts on the way. In this example, we’ll cover how to add a QR code to the widget that can, later on, be used to present any type of data, be it a link or a plain string message.

But wait. Before you sit down and start developing your widget, there are two requirements you need to know about.

  1. Your device or simulator has to run the iOS 14 operating system
  2. Your Xcode has to be updated to version 12.1

Also, note that we used a third-party library to generate the QR code.

Said that, let’s get started on the widget.

Setup

First things first, you will need to add a new target to the project, by clicking on File > New > Target and choose Widget Extension in the iOS tab, as done in the photo below.

After creating the new target it’s time to add the QR code library to the widget extension. I found that the best way to do that was to add the library using the Swift Package Manager. To do so, select your project in the project navigator and switch to the Swift Packages tab. By clicking the + button you will be asked to add the package repository URL (that can be found on the library’s GitHub in the installation section). The last step to incorporate the QR code library to the widget extension is to go to its target, click the + button in the Frameworks and Libraries section and choose it from the suggested list of libraries. 

Implementation

Moving on, we’ll go to the Widget.swift file where we’ll implement the presentation of the QR code on the widget itself. The first thing you may notice about this class is that the code is written in SwiftUI. Keep in mind that even if you haven’t had a chance to cross paths with SwiftUI before, you won’t need to make big changes to the code.

At the top of the class import your QR code library. Find the WidgetEntryView struct and delete the entire code leaving only the entry property and body view. For this example, we used the EFQRCode library for QR code generation. The QR code library creates image of type cgImage, so we created an additional method that allows us to generate the QR code and parse it to the type of UIImage, making it easier to work with and therefore show on the widget.

The last, but not least step is to use the newly generated QR Code image in the body. The resulting code is shown below.

Result

It’s time to see what we’ve done! 

Run your app on the simulator or device, and once it’s running, close it. Press and hold the screen until the apps on your home screen start to jiggle and the subtle + button appears in one of the top corners. Click on it and the new screen will be presented to you, holding all of the disposable widgets on the phone. Find the widget with the QR code, or in case it is not there find the name of your app, choose the size that fits your screen, and voilà! Your widget is done and ready to use.