xcstrings-tool
xcstrings-tool copied to clipboard
Local Package Previews Bundle issue: Fatal Error in resource_bundle_accessor.swift
Set Up
I have a Local Swift Package I use for separating my features and have a more quick iteration over features using local Previews that load fast and reliable because I don't need to build the whole project, nor include heavy 3rd party dependencies for my UI target.
Problem
One big issue is that Previews ran within a package rather than the main app have issues accessing values from a bundle like icons, fonts and translations. I used SwiftGen for everything, that works with some hacking using a custom bundle .myPackage
(see below), but it doesn't support xcassets yet. XCStrings Tool does, and works really well, but I cannot control the bundle.
Attempted Solution
For SwiftGen I can, and with the help of a custom bundle .myPackage
it works everywhere. I don't see a way to do this in XCStrings Tool. I cloned the repo and tried to hard code .myPackage
but I wasn't able to make it work inside my local package, perhaps because the binary version of the plug-in just works better in that scenario? So I'm not sure if that direction of solution would actually work for me.
Bundle.swift and Crash Log
Bundle.swift:
//
// Bundle.swift
//
//
// Created by Lucas van Dongen on 23/07/2024.
//
import Foundation
extension Bundle {
private class BundleFinder {}
}
extension Bundle {
static let myPackageBundleName = "HardwareIntegrationUI_HardwareIntegrationUI"
public static let myPackage: Bundle = {
let bundleNameIOS = myPackageBundleName
let candidates = [
// Bundle should be here when the package is linked into an App.
Bundle.main.resourceURL,
// Bundle should be here when the package is linked into a framework.
Bundle(for: BundleFinder.self).resourceURL,
// For command-line tools.
Bundle.main.bundleURL,
// Bundle should be here when running previews from a different package
// (this is the path to "…/Debug-iphonesimulator/").
Bundle(for: BundleFinder.self)
.resourceURL?
.deletingLastPathComponent()
.deletingLastPathComponent()
.deletingLastPathComponent(),
Bundle(for: BundleFinder.self)
.resourceURL?
.deletingLastPathComponent()
.deletingLastPathComponent(),
]
for candidate in candidates {
let bundlePathiOS = candidate?.appendingPathComponent(bundleNameIOS + ".bundle")
if let bundle = bundlePathiOS.flatMap(Bundle.init(url:)) {
return bundle
}
}
fatalError("Can't find myPackage custom bundle.")
}()
}
The pruned error report:
== PREVIEW UPDATE ERROR:
CrashReportError: Fatal Error in resource_bundle_accessor.swift
XCPreviewAgent crashed due to fatalError in resource_bundle_accessor.swift at line 44.
unable to find bundle named HardwareIntegration_HardwareIntegrationUI
Frames: [
Frame {
imageIndex: 9
imageOffset: 189728
symbol: _assertionFailure(_:_:file:line:flags:)
symbolLocation: 244
}
Frame {
imageIndex: 2
imageOffset: 3753152
symbol: closure #1 in variable initialization expression of static NSBundle.module
symbolLocation: 3372
sourceFile: resource_bundle_accessor.swift
sourceLine: 44
}
Frame {
imageIndex: 2
imageOffset: 3749764
symbol: one-time initialization function for module
symbolLocation: 12
sourceFile: resource_bundle_accessor.swift
sourceLine: 9
}
Frame {
imageIndex: 10
imageOffset: 15848
symbol: _dispatch_client_callout
symbolLocation: 16
}
Frame {
imageIndex: 10
imageOffset: 21980
symbol: _dispatch_once_callout
symbolLocation: 28
}
Frame {
imageIndex: 2
imageOffset: 3753608
symbol: NSBundle.module.unsafeMutableAddressor
symbolLocation: 80
sourceFile: resource_bundle_accessor.swift
sourceLine: 9
}
Frame {
imageIndex: 2
imageOffset: 3809132
symbol: static String.Localizable.BundleDescription.current.getter
symbolLocation: 144
sourceFile: Localizable.swift
sourceLine: 63
}