Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to make static library modular in Swift 4?

As after release of Swift 4, Swift is supporting Static library. But when I am trying to make use of Static binary inside application, it showing error with undefined module.

We are creating SDK with modular structure with 15 framework one for each module, but as Apple suggest it is not good to add more than 6 dynamic framework(As dynamic linking slow down app launch time.). So after support of static lib in Swift, we decided to convert it to static library and then create one dynamic framework which provide facade interface for all 15 frameworks.

I created one Static lib named StaticA an try to add it in Dynamic Framework, but it shows below error.

No such module 'StaticA'

enter image description here

I also set Defines Modules to Yes but it does not helping. Is it possible to make Static library modular using Swift ? If Yes, then suggest way. Thanks

enter image description here

like image 982
technerd Avatar asked Dec 05 '17 11:12

technerd


1 Answers

There's a few build settings you need to enable:

MODULEMAP_FILE = $(PRODUCT_NAME)/module.modulemap
SWIFT_INCLUDE_PATHS = $(PRODUCT_NAME)
DEFINES_MODULE = YES

The other option which works (without modifying the build settings) is to copy the modulemap file to the products directory under include/$(PRODUCT_NAME)

Note:

  • I generally put the modulemap in the top level of the module directory
  • i.e. one level down from the xcodeproj file:
    • StaticA.xcodeproj then I would have at StaticA/module.modulemap

What this allow's you to do is define a module.modulemap for your library:

module StaticA {
    header "StaticA-Swift.h"
}

Typically StaticA-Swift.h isn't available and won't be generated, you "might" be able to get away with not specifying it ... but I've not had any luck and have needed to do it manually.

You can use a script which will copy the generated *-Swift.h to the include folder so that you are able to reference it from your modulemap file.

#!/usr/bin/env sh

target_dir=${BUILT_PRODUCTS_DIR}/include/${PRODUCT_MODULE_NAME}/

# Ensure the target include path exists
mkdir -p "${target_dir}"

# Copy any file that looks like a Swift generated header to the include path
cp "${DERIVED_SOURCES_DIR}/"*-Swift.h "${target_dir}"
like image 118
Oliver Atkinson Avatar answered Oct 17 '22 12:10

Oliver Atkinson