Swift PM, Bundles and Resources

bundle
resources
linux

(Pedro José Pereira Vieito) #1

Once Swift Foundation PR #1573 and #1570 are merged we will be able to use Bundle API on Linux with Freestanding bundles. This means that with the following structure:

FooExecutable
FooExecutable.resources/Info.plist
FooExecutable.resources/FooResource.json
libBarLibrary.so
BarLibrary.resources/Info.plist
BarLibrary.resources/BarImage.png

We can access the resources with the Bundle API:

Bundle.main.path(forResource: "FooResource", withExtension: "json")
// .../FooExecutable.resources/FooResource.json

let barBundle = Bundle(for: BarLibraryClass.self)
barBundle.path(forResource: "BarImage", withExtension: "png")
// .../BarLibrary.resources/BarImage.png

This opens the way to the introduction of the Resources story of Swift PM. A first basic implementation could simply copy files found in a Resources directory of the target source folder to the respective TargetName.resources folder in the products directory.

Also, if we want to support this type of architecture we will have to start to rely in dynamic linking instead of static linking executable products (otherwise we would have to copy all the input resources to the executable resources directory, with potential collisions).

Finally, this approach would be designed for non-Darwin platforms (Darwin would have to use frameworks for libraries and app bundles? for executables as freestanding bundles are not welcome).


Evolution of Swift Evolution?
(Ankit Aggarwal) #2

Yep, bundle support in Linux will definitely open doors for resource support in SwiftPM. A couple of SwiftPM contributors are working on a draft proposal for resources. They expect to put it out for discussion this fall (it'll take some time due to upcoming vacations).


(Pedro José Pereira Vieito) #3

That's great! Looking forward for it :slight_smile:


(Karl) #4

This is awesome - once the package manager can support app/library bundles, it will be able to apply to so many more Swift projects.

@millenomi what did you mean by Darwin CLI tools having their own mechanism for resources? Are those resources accessible via the same CFBundle API? I don't think CLI tools are considered "bundles" on Darwin, so it would be nice if some other resource API (perhaps a SwiftPM runtime library) made that transparent to the developer.

Also: I'm very interested to see a proposal which brings resources to SwiftPM. It would be cool if we could do something like R.swift (https://github.com/mac-cain13/R.swift) and generate a file as part of the package-build process. This could maybe help abstract-away some details like asset catalogues.


(Lily Vulcano) #5

While this guarantee has been textually lost in the mist of time, and while command-line tool code isn't bundled, we consider the containing directory for a command-line tool to be its containing bundle, which is the one that'll be returned by Bundle.main. This holds true on Linux.


(Pedro José Pereira Vieito) #6

Well, this bundle flavour is probably the most "popular" one, as all iOS apps are of this type (simply a executable in a directory). The problem with this approach for CLI tools is that the executable is usually collocated with other executables/libraries so all of them would share the same Bundle resource path (the parent directory) and therefore collisions would be probable (for example, Info.plist).

The debate would be what's the better bundle flavour for each platform and product type:

Executable Library Application
Darwin ??? Framework App Bundle
Linux Freestanding / FHS Freestanding / FHS Freestanding / FHS
Windows Freestanding Freestanding Freestanding

(Lily Vulcano) #7

You're incorrect about iOS ('flat') bundles being the same as the fallback behavior for executables; we do special processing for either.

For Darwin command-line tools, the fallback bundle is rooted in that executable's directory, except that if the Mach-O binary has a __TEXT,__info_plist section, we use the content of that section to determine the content of Bundle's .infoDictionary.

For Linux, we do not support this — freestanding bundles are provided for use instead.


(Lily Vulcano) #8

Also, to be clear: whenever we say 'Linux' I actually mean 'Apple currently ships and supports Swift in Xcode and with tarballs for Linux, but this behavior isn't gated to a particular operating system'. The intent for FHS is that it apply wherever the FHS applies (Linux, FreeBSD and other 'nixes).


(Pedro José Pereira Vieito) #9

In what way do they behave different? In my understanding the only difference between version 3 and version 4 CFBundle is the existence of the Info.plist file.


(Pedro José Pereira Vieito) #10

So, for reference, the picture would look like this?

Executable Library Application
Darwin Unbundled (+ Mach-O __info_plist) Framework App Bundle
Linux et al. Freestanding / FHS Freestanding / FHS Freestanding / FHS
Windows Freestanding Freestanding Freestanding

(Reid Nantes) #11

@pvieitoci Any Idea when Swift Foundation PR #1573 and #1570 will be merged? I haven't seen activity since October.


(Pedro José Pereira Vieito) #12

@rnantes No idea. You should probably ask @millenomi or @Tony_Parker about that.


(Pedro José Pereira Vieito) #13

@Aciid There is any update on this?


(Thomas Krajacic) #14

Can SPM gain features like this in Swift's dot releases?

I'd say the prominent question is: "Will the next Xcode finally have SPM integration?"

That can only happen if SPM gains resource support (and possibly other features).

Since Xcode is being developed internally my best guess is that this feature hasn't happened yet because SPM more or less needs to coordinate with internal efforts?

It's been half a year since we got any statement from the SPM team about that topic. Could we get an update pretty please?

Of course we can see that in the meantime the SPM team has implemented great features that are fundamental to the future of SPM and possibly to Xcode integration! It's just the seemingly intentional silence on this topic is frustrating.

/cc @Aciid


(Anders Bertelrud) #15

There is a work-in-progress version of a draft proposal for SwiftPM resources, but it isn't yet ready for review. It's at https://github.com/abertelrud/swift-evolution/blob/package-manager-resources/proposals/NNNN-package-manager-resources.md if you want to take a look at the thinking around this so far.

This was written earlier in the year but had to be temporarily put on hold because of other priorities. The plan is to finish it up and send out for review, but there are some open questions in the proposal that should be addressed before asking everyone to take time to review it. We also want to make sure we have bandwidth to properly engage with the review discussion and feedback.

The silence around resources hasn't been intentional; it's been a matter of trying to split the time between that and other necessary work on SwiftPM.


(Thomas Krajacic) #16

This is a great read! Thank you for sharing!

I see that by the amount of open questions this will most likely not fit into the Swift 5 timeframe. That's fine I guess, but I think that involving the community rather earlier than later on these open questions would still have been valuable.

Also it would be great to have some sense of what the priorities of features is that the team is working on :slight_smile:


(Pedro José Pereira Vieito) #17

Thanks for sharing, it looks promising!