静态库和 Swift
Posted
技术标签:
【中文标题】静态库和 Swift【英文标题】:Static Library and Swift 【发布时间】:2015-06-22 23:06:45 【问题描述】:所以我正在使用 Swift 开发一个 ios 项目,我想创建一个包含一些有用内容的静态库。
我的问题是,当我尝试在 Xcode(6.3 版)中构建我的库时,出现“构建失败”,然后是:/Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/bin/libtool: unknown option character 'X' in: -Xlinker
我从来没有见过这个,它不是我的第一个静态库。所以我想我可能与我只使用 Swift 类这一事实有关。
你们怎么看? 提前谢谢你。
【问题讨论】:
接受的答案不再准确。从 Xcode 9 beta 4 开始,Swift 可以在静态库中使用,尽管有些场景需要额外的配置。请参阅下面的答案。 【参考方案1】:如上所述,Apple确实从 Xcode 9 Beta 4 开始允许在静态库中使用 Swift。
我们尝试在现有项目上使用基于 Objective-C 的目标和“子”静态库项目执行此操作,但一直遇到链接错误
ld: library not found for -lswiftSwiftOnoneSupport for architecture x86_64
还有
ld: library not found for -lswiftDispatch for architecture x86_64
这是因为主要目标(应用程序)试图仅针对 Objective-C 进行构建,而静态库并未告知它需要包含 Swift 库。这是因为应用目标的Build Phases
的Compile Sources
部分中没有任何Swift 文件。
所以基本上您所要做的就是在该编译列表中添加至少一个.swift
文件,它会为您包含 Swift 库。它甚至不需要任何代码或值,它可以是一个空文件。
然后您可以开始将 Swift 文件添加到您的“子”静态库项目中。我会让它首先为您生成桥接头,然后您可以移动它并更改导入的内容(如果您移动它,请确保项目指向构建设置中的正确文件)。
您仍然应该记住,在 same 静态库中使用 Swift 和 Objective-C 可能会遇到问题。我建议阅读the Apple developer doc "Swift and Objective-C in the Same Project",了解如何解决将Objective-C 导入Swift(使用桥接头)以及如何在Objective-C 代码中使用Swift 文件(为您的库导入生成的-Swift.h
)。
【讨论】:
就我而言,我看到的是ld: library not found for -lswiftCoreImage for architecture x86_64
。这个答案解决了我的链接问题。
@afarnham 我认为它会为 Swift“核心”中的几乎每个库都这样做,因为它在从使用 Swift 的静态库中链接内容时尝试与它们链接。我之前尝试手动将每个 Swift 库包含在目标依赖项和其他构建阶段中;不用说这是一场噩梦……而且没有用。我希望 Apple 将其设为项目设置,这样您就不必准备一个虚拟文件来“欺骗”主要目标,但我猜这目前可行。
我只有一个混合了objective-c和swift的静态库,我无法编译项目(react-native):)
太棒了,只需添加一个空的 Swift 文件,所有这些错误都会消失。感谢您的帮助!
我羡慕@thibautnoah。我已经有这个问题好几个星期了!谢谢一百万!【参考方案2】:
Swift 没有 support static library
虽然正确的方法应该是创建框架,但有一个解决方法here。
【讨论】:
这很烦人。谢谢你的回答。 您好,由于 swift 不支持静态库,如何防止同事阅读我的代码? (这是关于加密数据的,所以知道的人越少越好)。我的应用也支持 ios 7,所以我想我不能使用框架,对吧? 可能需要更新到现在? swift 现在支持框架和静态库吗? 从objective c 项目中我们可以创建静态库,但是否可以从xcode 8 开始的Swift 项目中创建静态库 在 swift 3 中是否有任何使用静态库的解决方案,我有一个加密库,其中只有两个 .a 文件在供应商样本(用 Objective-c 编写)是工作文件,当我尝试使用那些使用桥接头的库,(显然桥接头配置很好,因为其他objective-c库工作正常),它不能抛出错误。任何人对此问题都有解决方案,然后请发布一些线索。【参考方案3】:从 Xcode 9 beta 4 开始,Xcode 原生支持带有 Swift 源代码的静态库。
【讨论】:
我必须做什么才能启用它?使用包含 swift 的静态库时,如何访问 Objective-c 项目中的标头? @HariKaramSingh 我在单独的答案中回答了 OP 问题和你的问题。 对我来说,这个问题在 Xcode 9.2 (9C40b) 上再次出现,在pod update
之后。可能我正在使用的 swift pod 更改了设置。【参考方案4】:
Swift 消费者 -> Swift 静态库
Xcode 版本 10.2.1
创建 Swift 静态库
创建库项目或创建库目标
File -> New -> Project... -> Cocoa Touch Static Library
//or
Project editor -> Add a Target -> Cocoa Touch Static Library
添加文件.swift
Select `.swift` file -> Select File Inspectors Tab -> Target Membership -> Select the target
//or
Project editor -> select a target -> Build Phases -> Compile Sources -> add files
构建库 - ⌘ 命令 + B 或Product -> Build
注意 1:确保为与客户端代码相同的流程架构构建库。
注意 2:使用 public
或 open
访问修饰符[About] 公开您应该对消费者可见的 API
查找生成的输出[Build location]
Products group -> lib<product_name>.a -> Show in Finder
目录包括
lib<product_name>.a
– 内置静态库
<product_name>.swiftmodule
。 swiftmodule
描述了库的接口和编译器版本。该文件夹包括:
.swiftdoc
- 文档
.swiftmodule
- 公共接口/定义
带有 Swift 静态库的 Swift 消费者
Drag and drop
二进制进入Xcode项目[About]
Link Binary
[Undefined symbols][Link vs Embed]
Project editor -> select a target -> General -> Linked Frameworks and Libraries -> add -> Add Others... -> point to `lib<target_name>.a` file
//or
Project editor -> select a target -> Build Phases -> Link Binary With Libraries -> add -> Add Others... -> point to `lib<target_name>.a` file
添加Library Search paths(LIBRARY_SEARCH_PATHS)
[Library not found for][Recursive path]
Project editor -> select a target -> Build Settings -> Search Paths -> Library Search paths -> add path to the parent of `lib<target_name>.a` file
添加Import Paths
[No such module][Recursive path]
Project editor -> select a target -> Build Settings -> Swift Compiler - Search Paths -> Import Paths -> add path to a folder with `.swiftmodule`
将模块导入Swift客户端代码[module_name]
import module_name
[More examples]
【讨论】:
我已经在自己的独立项目中构建了静态框架。我看到了.a
文件和.swiftmodule
文件夹。我应该将它们都拖到我的主机应用程序中,然后尝试查找路径。对吗?
抱歉,请问有什么注意事项吗?
你好@Honey,我会再次检查并提供信息
@Honey,回答您的问题,在构建库后,您应该执行 3 个步骤: 1. 将 .a
文件拖到您的主机应用程序中的 Linked Frameworks and Libraries
部分下。 2. 在Library Search paths
部分下指定.a
fine 的路径 3. 在Import Paths
部分下指定.swiftmodule
fine 的路径。我刚刚检查了教程并更新了一篇文章。如果您有任何问题,请随时询问
@yoAlex5,非常感谢您详细而全面的解释。我唯一要补充的是,您不要忘记标记您的类和方法public
以使它们在其他目标中可用。没有它,您将能够导入库,但不能使用它的代码。另外,请注意init
s 必须明确公开。以上是关于静态库和 Swift的主要内容,如果未能解决你的问题,请参考以下文章
iOS XCode7制作.Framework动态库和.a静态库的总结