@import

Toy Swift Module

Logger

log

Logger.swiftmodule

Logger.swiftdoc

libLogger.a

dylib

xcrun

swift

sudo xcode-select -switch $xcode_dir/Contents/Developer

libLogger.a

Logger

class Logger { var prefix: String init(_ prefix: String) { self.prefix = prefix } func log<T>(object: T) { print(prefix) println(object) } }

var logger = Logger("> ") logger.log("Hello, World!")

libLogger.a

xcrun swift -emit-library -emit-object Logger.swift -sdk $(xcrun --show-sdk-path --sdk macosx) -module-name Logger ar rcs libLogger.a Logger.o

-emit-library

-emit-object

main

-emit-object

-emit-library

Logger.swiftmodule

xcrun swift -emit-module Logger.swift -sdk $(xcrun --show-sdk-path --sdk macosx) -module-name Logger

Logger.swiftdoc

Logger.swiftmodule

import Foundation import Logger var logger = Logger("> ") logger.log("Hello")

> Hello

libLogger.a

-lLogger

Logger.swiftdoc

///

/// Simple Logger /// /// Constructor takes prefix string which will be printed before actual object /// class Logger { var prefix: String init(_ prefix: String) { self.prefix = prefix } /// Prints `object` with specified `prefix` func log<T>(object: T) { print(prefix) println(object) } }

Conclusion

jar

import Foundation /// Simple Logger /// /// Constructor takes prefix string which will be printed before actual object /// class Logger { var prefix: String init(_ prefix: String) { self.prefix = prefix } /// Prints `object` with prefix func log<T>(object: T) { print(prefix) println(object) } }

/// Simple Logger /// /// Constructor takes prefix string which will be printed before actual object /// class Logger { var prefix: String init(_ prefix: String) /// Prints `object` with prefix func log<T>(object: T) }

If you have already started playing with swift, you probably thought about how to include third party libraries into your project or how to distribute yours.Apple provides a mechanism to distribute code via frameworks (eventually, for iOS too), so making a custom framework, which will include both ObjC and Swift code is very easy. But let’s dig deeper and create aSwift module, like apple does with Swift’ std lib and Cocoa/CocoaTouch bridge.this module will work in swift-only projects, in case if ObjC compiler generates Swift-to-ObjC bridging header and includes swift-module viadirective, which doesn’t work with current Xcode/Apple Clang version.We’re going to create a simple module callwhich will contain only one method:.You can see sample project here .Each swift module consists of at least three files, so we should get all of them as an output:– public interface/definitions– docs (surprisingly)– built library (there also might be a, it depends on your task)you should switchto beta xcode’ version before runningcommandsLet’s create the simplest and useless“library”.The class just takes some prefix and logs it before actual objectNow it’s time to make agenerates dynamically linked shared library, whilegenerates object file, so you will have linker errors due to duplicated symbols.Solution is pretty simple: include both flagsand, as I did above.This command will generateand.Now we have complete module and can integrate it into real project. Just create simple swift-project and add the files: Then setup ‘Import paths’ for Swift We’re ready to check how it works:Just run and you’ll see an expected output:If you see linker errors, check your ‘Library search paths’ and ‘Other linker flags’ — they should contain path toandrespectively.Let’s figure out how to deal with documentation.To add documentation to module you just need to comment it using, e.g.:After integrating module into a project you will see documentation on the right But I didn’t manage to get it work without restarting Xcode after integrating.This approach is not very nice for “everyday” usage for a regular iOS/OSX developer (because it requires creating and supporting Make/CMake file), but it might be useful if you want to create pure module which doesn’t use ObjC at all.Also, Swift modules are similar to Java’sbinaries.The source code:transforms into module interface without details of implementationSo you can even distribute proprietary libraries without any problems (except of crazy reverse engineers), but I hope you won’t do this in favor of Open Source Software ;)