组件化开发之-如何解决Swift/OC-Framenwork/Library混合创建pod问题

原创 2017-06-28

关键点

  • Swift依赖第三方Objective-C Framework、Library创建Pod
  • Swift与Objective-C代码混合创建Pod
  • Swift与OC、第三方Framework/Library混合创建Pod

在我的另一篇文章中介绍到了如何创建自己的公有、私有Pod,我以为创建Pod的坑就可以很简单的跳过,但是事情不是这样子的,在使用组件化开发私有组件的时候我又遇到了新问题(由于项目采用的是Objective-C开发):

  • 业务组件依赖其他第三方厂家提供的OC Frameworwk、Library,这些第三方只提供了OC工具包,这个时候我们应该怎样让他集成到我们自己的其中一个业务组建中?
  • 在私有业务组件开发中,遇到了项目急需演示验收,这个时候你并没有足够的时间采用Swift来实现你的业务(已经实现了一部分),但是在以前的OC开发项目中,你已经实现了此业务另一部分,现在你需要做的是把它们拿过来集成到你现在开发的一个业务组件中来 ,但是如何集成呢?

下面来说一说解决办法:

准备工作

在这里我们需要有一个Development Pod让我们来进行开发、测试,首先我们通过pod lib 来创建一个Pod,使其包含Example,Pods等,当然你也可以自己手动完成这一系列事情。

pod lib create Verify-SwiftOC3rd
Cloning `https://github.com/CocoaPods/pod-template.git` into `Verify-SwiftOC3rd`.
Configuring Verify-SwiftOC3rd template.

------------------------------

To get you started we need to ask a few questions, this should only take a minute.

If this is your first time we recommend running through with the guide:
 - http://guides.cocoapods.org/making/using-pod-lib-create.html
 ( hold cmd and click links to open in a browser. )


What language do you want to use?? [ Swift / ObjC ]
 > Swift

Would you like to include a demo application with your library? [ Yes / No ]
 > Yes

Which testing frameworks will you use? [ Quick / None ]
 > None

Would you like to do view based testing? [ Yes / No ]
 > No

Running pod install on your new library.

上述所有的步骤你只需要按照提示信息完成即可,创建成功后将会自动打开项目,最后你看到的将会是:


image

然后我们将其与Github关联起来,你需要在github上创建一个新的Repo - Verify-SwiftOC3rd

$ git remote add origin git@github.com:ApterKingRepo/Verify-SwiftOC3rd.git

接下来将.podspec 稍加修改:将其中的homepage,source等信息配置一下,最后验证修改是否正确,然后提交代码:

$ pod lib lint --swift-version=3.0

 -> Verify-SwiftOC3rd (0.1.0)

Verify-SwiftOC3rd passed validation.

$ git add .
$ git commit -m "Initial"
$ git push

至此准备工作完成!

Swift依赖第三方Objective-C Framework、Library创建Pod

在制作我自己私有Pod时,我们往往需要用到第三方提供的工具包,比如说网络请求Moya,数据解析SwiftyJSON,响应式编程(RP) RxSwfit等,对于这些框架的使用我们在制作创建我们Pod的时候,往往只需要在我们的.podspec中dependency既可以了,如我在SwiftyJSON基础之上创建的SwiftyJSONMappable(用于JSON与Model互相转换,并且提供了与Moya的配合使用)这个Pod,我只需要在我的Pod中使用dependency 即可:

Pod::Spec.new do |s|
  ...
  // 此处省略
  ...  
  s.requires_arc = true
  s.default_subspec = "Mappable"

  s.subspec "Mappable" do |ss|
    ss.source_files = "Pod/Classes/JSONMappable.swift"  
    ss.dependency "SwiftyJSON", "~>3.1.4"
    ss.frameworks = "Foundation"
  end
  ...
end

当在创建我们自己的Pod时,Pod会自己检测并且install我所引用到的第三方仓库,一切顺利。但是也许你会使用到像百度地图高德地图ShareSDK分享等使用Framework以及library方式集成的第三方库,它们其中有些是提供了你使用Pod方式导入的,可能你会想到直接dependency一下,这里我们就来以百度地图为例做一个验证:

Pod::Spec.new do |s|

   ...

  s.requires_arc = true
  s.dependency "BaiduMapKit"   // 主要看这里就好

end

现在你想到的应该是执行pod lib lint就可以了吧,ok我们来执行以下

$ pod lib lint Verify-SwiftOC3rd.podspec

 -> Verify-SwiftOC3rd (0.0.1)
    - ERROR | [iOS] unknown: Encountered an unknown error (The 'Pods-App' target has transitive dependencies that include static binaries: (/private/var/folders/pq/1jkyxxs52bd9c4jykqvgfqbw0000gn/T/CocoaPods/Lint/Pods/BaiduMapKit/BaiduMapKit/thirdlibs/libcrypto.a, /private/var/folders/pq/1jkyxxs52bd9c4jykqvgfqbw0000gn/T/CocoaPods/Lint/Pods/BaiduMapKit/BaiduMapKit/thirdlibs/libssl.a, /private/var/folders/pq/1jkyxxs52bd9c4jykqvgfqbw0000gn/T/CocoaPods/Lint/Pods/BaiduMapKit/BaiduMapKit/BaiduMapAPI_Base.framework, /private/var/folders/pq/1jkyxxs52bd9c4jykqvgfqbw0000gn/T/CocoaPods/Lint/Pods/BaiduMapKit/BaiduMapKit/BaiduMapAPI_Cloud.framework, /private/var/folders/pq/1jkyxxs52bd9c4jykqvgfqbw0000gn/T/CocoaPods/Lint/Pods/BaiduMapKit/BaiduMapKit/BaiduMapAPI_Location.framework, /private/var/folders/pq/1jkyxxs52bd9c4jykqvgfqbw0000gn/T/CocoaPods/Lint/Pods/BaiduMapKit/BaiduMapKit/BaiduMapAPI_Map.framework, /private/var/folders/pq/1jkyxxs52bd9c4jykqvgfqbw0000gn/T/CocoaPods/Lint/Pods/BaiduMapKit/BaiduMapKit/BaiduMapAPI_Radar.framework, /private/var/folders/pq/1jkyxxs52bd9c4jykqvgfqbw0000gn/T/CocoaPods/Lint/Pods/BaiduMapKit/BaiduMapKit/BaiduMapAPI_Search.framework, and /private/var/folders/pq/1jkyxxs52bd9c4jykqvgfqbw0000gn/T/CocoaPods/Lint/Pods/BaiduMapKit/BaiduMapKit/BaiduMapAPI_Utils.framework)) during validation.

[!] Verify-SwiftOC3rd did not pass validation, due to 1 error.
You can use the `--no-clean` option to inspect any issue.

结果是验证不通过!!!为什么呢?那是因为在Pod中你是使用了动静态库.framework、.a,这个是在制作Pod时需要指明的,你需要使用到(官方文档可查):

vendored_frameworks = "xxx.framework"
vendored_libraries = "xxx.a"

他们需要的是一个路径,相对路径,也就是说如果你在制作Pod时,如果第三方工具包使用的是动态库.framework或者静态库.a,那么你就不能简单的通过dependency方式来引入它了,不管它是Objective-C还是Swift Language,你现在要做的是下载到他们的framewor或者library,然后通过上面的一种或者两种方式来引入进来,对于这个问题,我想就使用百度地图来说明一下解决情况吧:

  • 首先你需要根据自己的需求去官网下载百度地图SDK(这里我只下载基础地图包)
  • 将其放置于你需要制作Pod项目的一个子目录下

处理完成之后项目目录结构大致是:

image
  • 修改.podspec文件

我这里把百度地图制作成为一个subspec,当然你也可以不用这样,我这样做的原因是:因为我还有我与业务相关的source_files,我把百度地图作为一个subspec更好区分一点而已


Pod::Spec.new do |s|

  s.name         = "Verify-SwiftOC3rd"
  s.version      = "0.0.1"
  s.summary      = "验证私有组件中使用Swift结合OC第三方.framewor、.library库及OC文件组合打包构建私有Pod"
  ...

  s.requires_arc = true

  s.subspec 'BaiduMapKit' do |ss|   
    ss.source_files = ''Verify-SwiftOC3rd/Vendors/*.framework/Headers/**.h'
    ss.public_header_files = ''Verify-SwiftOC3rd/Vendors/*.framework/Headers/**.h'

    ss.frameworks   =  'CoreLocation', 'QuartzCore', 'OpenGLES', 'SystemConfiguration', 'CoreGraphics', 'Security', 'CoreTelephony'
    ss.libraries    = 'sqlite3.0', 'stdc++.6.0.9'

    ss.vendored_frameworks =  'Verify-SwiftOC3rd/Vendors/*.framework'
    ss.vendored_libraries = 'Verify-SwiftOC3rd/Vendors/thirdlibs/*.a'

    ss.preserve_paths = 'Verify-SwiftOC3rd/Vendors/*.framework', 'Verify-SwiftOC3rd/Vendors/thirdlibs/*.a'
    ss.pod_target_xcconfig = { 'LD_RUNPATH_SEARCH_PATHS' => '$(PODS_ROOT)/Verify-SwiftOC3rd/Vendors/' }
  end

end

好了现在让我们来验证一下是否可以成功:

$  pod lib lint

 -> Verify-SwiftOC3rd (0.1.0)
    - ERROR | [iOS] xcodebuild: Returned an unsuccessful exit code. You can use `--verbose` for more information.
    - NOTE  | xcodebuild:  <module-includes>:1:9: note: in file included from <module-includes>:1:
    - NOTE  | xcodebuild:  /Users/wangcong/Library/Developer/Xcode/DerivedData/App-bqxcyvfrcjeqxqbqkrseipvvyrla/Build/Products/Release-iphonesimulator/Verify-SwiftOC3rd/Verify_SwiftOC3rd.framework/Headers/Verify-SwiftOC3rd-umbrella.h:22:9: note: in file included from /Users/wangcong/Library/Developer/Xcode/DerivedData/App-bqxcyvfrcjeqxqbqkrseipvvyrla/Build/Products/Release-iphonesimulator/Verify-SwiftOC3rd/Verify_SwiftOC3rd.framework/Headers/Verify-SwiftOC3rd-umbrella.h:22:
    - NOTE  | xcodebuild:  /Users/wangcong/Library/Developer/Xcode/DerivedData/App-bqxcyvfrcjeqxqbqkrseipvvyrla/Build/Products/Release-iphonesimulator/Verify-SwiftOC3rd/Verify_SwiftOC3rd.framework/Headers/BMKArcline.h:9:9: note: in file included from /Users/wangcong/Library/Developer/Xcode/DerivedData/App-bqxcyvfrcjeqxqbqkrseipvvyrla/Build/Products/Release-iphonesimulator/Verify-SwiftOC3rd/Verify_SwiftOC3rd.framework/Headers/BMKArcline.h:9:
    - ERROR | [iOS] xcodebuild:  /Users/wangcong/Library/Developer/Xcode/DerivedData/App-bqxcyvfrcjeqxqbqkrseipvvyrla/Build/Products/Release-iphonesimulator/Verify-SwiftOC3rd/Verify_SwiftOC3rd.framework/Headers/BMKMultiPoint.h:10:9: error: include of non-modular header inside framework module 'Verify_SwiftOC3rd.BMKMultiPoint': '../../../../../../../../../Users/wangcong/Development/iOS/Verify/Verify-SwiftOC3rd/Verify-SwiftOC3rd/Vendors/BaiduMapAPI_Base.framework/Headers/BMKTypes.h'

完美的出现了两个错误

  • include of non-modular header inside framework module 'xxx.framework'
  • error: redefinition of enumerator 'BMK_COORDTYPE_GPS'

要解决这两个错误很简单,你只需要去掉你BaiduMapKit中的两个参数ss.source_files以及ss.public_header_files

Pod::Spec.new do |s|

  s.name         = "Verify-SwiftOC3rd"
  s.version      = "0.0.1"
  s.summary      = "验证私有组件中使用Swift结合OC第三方.framewor、.library库及OC文件组合打包构建私有Pod"
  ...

  s.requires_arc = true

  s.subspec 'BaiduMapKit' do |ss|   
    ss.frameworks   =  'CoreLocation', 'QuartzCore', 'OpenGLES', 'SystemConfiguration', 'CoreGraphics', 'Security', 'CoreTelephony'
    ss.libraries    = 'sqlite3.0', 'stdc++.6.0.9'

    ss.vendored_frameworks =  'Verify-SwiftOC3rd/Vendors/*.framework'
    ss.vendored_libraries = 'Verify-SwiftOC3rd/Vendors/thirdlibs/*.a'

    ss.preserve_paths = 'Verify-SwiftOC3rd/Vendors/*.framework', 'Verify-SwiftOC3rd/Vendors/thirdlibs/*.a'
    ss.pod_target_xcconfig = { 'LD_RUNPATH_SEARCH_PATHS' => '$(PODS_ROOT)/Verify-SwiftOC3rd/Vendors/' }
  end

end

是什么原因呢?在创建Pod时候,我们并不需要创建xxx-Bridge-Header, 这个工作交由xxx-umbrella.h完成,这个文件的作用是:混合你的Swift以及OC,并且向外界暴露你的APIs,当你再次通过ss.source_files以及ss.public_header_files时会重复定义,现在我们去掉之后来试试是否能够成功:

$ pod lib lint

 -> Verify-SwiftOC3rd (0.1.0)

Verify-SwiftOC3rd passed validation.

OK , 成功!接下来将你的代码push到名叫Verify的specs中

$ git add .
$ git commit -m "提交百度.framework、.a 并且完成subspec BaiduMapKit"
$ git push    // 这里会等上一会
$ git tag 0.1.0
$ git push --tags
Total 0 (delta 0), reused 0 (delta 0)
To git@github.com:ApterKingRepo/Verify-SwiftOC3rd.git
 * [new tag]         0.1.0 -> 0.1.0

$ pod repo push Verify Verify-SwiftOC3rd.podspec
  • 现在你我们来验证是否可以使用了:
image

编译运行,一切OK!到这里已经算是可以使用了。这里我们来进行稍微的优化一下,你可能会想到如果你的项目是采用Swift来完成的,那么你就必须需要创建xxx-Bridge-Heder.h,有没有一种方式是可以不需要Bridge-Header的呢?这里我么使用创建一个.modulemap来解决进行优化:

  • 修改.podspec,为你所引用到的framework创建Module,这里我把.podsepc全部提出来,为了使你了解的更明白:

注意:
如果我们手动创建一个module文件,直接移进去。这样会导致 pod install 时可能丢失该文件,那么该怎么办呢?我们需要使用的是prepare_command,来帮助我们自动创建



Pod::Spec.new do |s|
  s.name             = 'Verify-SwiftOC3rd'
  s.version          = '0.1.4'
  s.summary          = '验证私有组件中使用Swift结合OC第三方.framework、.library库及OC文件组合打包构建私有Pod'

  s.homepage         = 'https://github.com/ApterKingRepo/Verify-SwiftOC3rd'
  s.license          = { :type => 'MIT', :file => 'LICENSE' }
  s.author           = { 'ApterKing' => 'wangcccong@outlook.com' }
  s.source           = { :git => 'https://github.com/ApterKingRepo/Verify-SwiftOC3rd.git', :tag => s.version.to_s }

  s.ios.deployment_target = '8.0'

  s.source_files = 'Verify-SwiftOC3rd/Vendors/*.framework/Headers/**.h'
  s.public_header_files = 'Verify-SwiftOC3rd/Vendors/*.framework/Headers/**.h'
  s.resources = 'Verify-SwiftOC3rd/Vendors/*.framework/Resources/mapapi.bundle'
  
  s.frameworks   =  'CoreLocation', 'QuartzCore', 'OpenGLES', 'SystemConfiguration', 'CoreGraphics', 'Security', 'CoreTelephony'
  s.libraries    = 'sqlite3.0', 'stdc++.6.0.9'

  s.vendored_frameworks =  'Verify-SwiftOC3rd/Vendors/*.framework'
  s.vendored_libraries = 'Verify-SwiftOC3rd/Vendors/thirdlibs/*.a'

  s.prepare_command = <<-EOF
    # 创建Base Module
    rm -rf Verify-SwiftOC3rd/Vendors/BaiduMapAPI_Base.framework/Modules
    mkdir Verify-SwiftOC3rd/Vendors/BaiduMapAPI_Base.framework/Modules
    touch Verify-SwiftOC3rd/Vendors/BaiduMapAPI_Base.framework/Modules/module.modulemap
    cat <<-EOF > Verify-SwiftOC3rd/Vendors/BaiduMapAPI_Base.framework/Modules/module.modulemap
    framework module BaiduMapAPI_Base {
      umbrella header "BMKBaseComponent.h"
      export *
      link "sqlite3.0"
      link "stdc++.6.0.9"
    }
    \EOF

    # 创建Map Module
    rm -rf Verify-SwiftOC3rd/Vendors/BaiduMapAPI_Map.framework/Modules
    mkdir Verify-SwiftOC3rd/Vendors/BaiduMapAPI_Map.framework/Modules
    touch Verify-SwiftOC3rd/Vendors/BaiduMapAPI_Map.framework/Modules/module.modulemap
    cat <<-EOF > Verify-SwiftOC3rd/Vendors/BaiduMapAPI_Map.framework/Modules/module.modulemap
    framework module BaiduMapAPI_Map {
      umbrella header "BMKMapComponent.h"
      export *
      link "sqlite3.0"
      link "stdc++.6.0.9"
    }
    \EOF

  EOF

end
  • pod install,测试是否可以使用
image

Swift与Objective-C代码混合创建Pod

接下来我们还需要来解决文章开头提到的第二个问题,那就是如何将Swfit于OC代码混合打包(我们这一步只验证Swift与OC混合打包),在这里就直接使用上述所创建的工程,不过我们需要的先将上述与百度地图有关的信息删除,然后修改Pod文件:

  • 删除Vendors文件夹
  • 修改.podspec

Pod::Spec.new do |s|
  s.name             = 'Verify-SwiftOC3rd'
  s.version          = '0.1.1'
  s.summary          = '验证私有组件中使用Swift结合OC第三方.framework、.library库及OC文件组合打包构建私有Pod'

  s.homepage         = 'https://github.com/ApterKingRepo/Verify-SwiftOC3rd'
  s.license          = { :type => 'MIT', :file => 'LICENSE' }
  s.author           = { 'ApterKing' => 'wangcccong@outlook.com' }
  s.source           = { :git => 'https://github.com/ApterKingRepo/Verify-SwiftOC3rd.git', :tag => s.version.to_s }
  # s.social_media_url = 'https://twitter.com/<TWITTER_USERNAME>'

  s.ios.deployment_target = '8.0'
  s.source_files = 'Verify-SwiftOC3rd/Classes/**/*'
  # s.public_header_files = 'Pod/Classes/**/*.h'

end

注:
可以不用通过pod repo push 之后再来验证创建的Pod添加的代码是否正确,在你通过pod lib create POD_NAME 中是可以直接修改本地.podspec,然后在Example目录下直接pod install,这个验证比较方便,快捷,不用依赖网络

  • 接下来创建一个PersonProtocol、Kid,使Kid实现PersonProtocol协议
  • 完成上述步骤后,你当然是希望外部也能够访问到我的文件,那该如何处理呢?现在只需要将他们的.h文件设置为public,如下图:
image
  • 这个时候你执行pod install,然后打开你的xxx-unbrella.h,你会发现上述两个文件的头文件已经被引入进来了,你可以把xxx-unbrella.h看成是你的项目头文件或者在Swift项目中他充当一个xxx-Bridge-Header.h文件
image
  • 接下来实现Swift对OC的引用,如果是Swift代码我们是不需要像OC一样设置其为public的只需要定义其访问权限即可,但是需要勾选其Target Membership。我在这里创建一个Woman,使其有一个小孩Kid并且实现PersonProtocol,然后喂养这个小孩吃饭:
image

编译发现会出现以下错误:


image

只需要按照提示创建一个即可


image
  • 实现Objective-C调用Swift,为了凑成一个家庭,我还创建了一个Father.swift类, Family使用OC Language,它包含了Kid、Mother、Father这三个类,最后结构如下:
image

编译运行,你会发现上述错误,找不到你的ProjectName-Swift.h。原因有两点:一是在你的ProjectName-Swift.h中是引用了Family.h的,如果你这时候在定义Family.h中又引用ProjectName-Swift.h造成了有点像循环引用的概念;


Swift与OC互相调用流程
image

二是Swift只支持动态库(并非完全意义的动态库),而我们代码在Pod之后实际上是一个动态的Framework,Swift是有命名空间的一个概念,这时候你需要做的是在引用时需要写明命名空间。基于上述两点,我们只能在OC的.m文件中引用并且加上命名空间:

image
  • 最后我们在Example目录下 Pod install,在项目中引用Family,然后来验证我们这个Pod是否创建成功
image

Swift与OC 代码、 Framework、Library混合创建Pod

上述两个分别讲解了Swift与OC代码混合创建Pod,Swift与OC Framework、Library混合创建Pod,现在我们来将三者混合创建,这里也就是我们解决了三种:

  • Swift引用第三方Framework、Library
  • Swift与Objective-C 在Pod相互调用
  • Swift与Objective-C 在项目、Pod相互调用Framework、Library、代码

依照上述两个章节所讲,我的.podspec如下:


Pod::Spec.new do |s|
  s.name             = 'Verify-SwiftOC3rd'
  s.version          = '0.1.4'
  s.summary          = '验证私有组件中使用Swift结合OC第三方.framework、.library库及OC文件组合打包构建私有Pod'

  s.homepage         = 'https://github.com/ApterKingRepo/Verify-SwiftOC3rd'
  s.license          = { :type => 'MIT', :file => 'LICENSE' }
  s.author           = { 'ApterKing' => 'wangcccong@outlook.com' }
  s.source           = { :git => 'https://github.com/ApterKingRepo/Verify-SwiftOC3rd.git', :tag => s.version.to_s }

  s.ios.deployment_target = '8.0'

  s.source_files = 'Verify-SwiftOC3rd/Classes/**/*', 'Verify-SwiftOC3rd/Vendors/*.framework/Headers/**.h'
  s.public_header_files = 'Verify-SwiftOC3rd/Classes/**/*.h', 'Verify-SwiftOC3rd/Vendors/BadiduMapAPI_Base.framework/Headers/BMKBaseComponent.h', 'Verify-SwiftOC3rd/Vendors/BadiduMapAPI_Map.framework/Headers/BMKMapComponent.h'
  s.resources = 'Verify-SwiftOC3rd/Vendors/BaiduMapAPI_Map.framework/Resources/mapapi.bundle'
#s.module_name = 'BaiduMapKit'

  s.frameworks   =  'CoreLocation', 'QuartzCore', 'OpenGLES', 'SystemConfiguration', 'CoreGraphics', 'Security', 'CoreTelephony'
  s.libraries    = 'sqlite3.0', 'stdc++.6.0.9'

  s.vendored_frameworks =  'Verify-SwiftOC3rd/Vendors/*.framework'
  s.vendored_libraries = 'Verify-SwiftOC3rd/Vendors/thirdlibs/*.a'

  s.preserve_paths = 'Verify-SwiftOC3rd/Vendors/*.framework', 'Verify-SwiftOC3rd/Vendors/thirdlibs/*.a'
  s.pod_target_xcconfig = {
#'FRAMEWORK_SEARCH_PATHS' => '${PODS_ROOT}/Verify-SwiftOC3rd/Vendors',
            'HEADER_SEARCH_PATHS' => '$(PODS_ROOT)/Verify-SwiftOC3rd/Vendors/*.framework/Headers',
            'LD_RUNPATH_SEARCH_PATHS' => '$(PODS_ROOT)/Verify-SwiftOC3rd/Vendors/',
            'OTHER_LDFLAGS' => '-ObjC'
  }

  s.prepare_command = <<-EOF

    # 业务Module
    rm -rf Verify-SwiftOC3rd/Classes/Modules
    mkdir Verify-SwiftOC3rd/Classes/Modules
    touch Verify-SwiftOC3rd/Classes/Modules/module.modulemap
    cat <<-EOF > Verify-SwiftOC3rd/Classes/Modules/module.modulemap
    framework module Verify {
      umbrella header "Verify_SwiftOC3rd.h"
      export *
      link "sqlite3.0"
      link "stdc++.6.0.9"
    }
    \EOF


    # 创建Base Module
    rm -rf Verify-SwiftOC3rd/Vendors/BaiduMapAPI_Base.framework/Modules
    mkdir Verify-SwiftOC3rd/Vendors/BaiduMapAPI_Base.framework/Modules
    touch Verify-SwiftOC3rd/Vendors/BaiduMapAPI_Base.framework/Modules/module.modulemap
    cat <<-EOF > Verify-SwiftOC3rd/Vendors/BaiduMapAPI_Base.framework/Modules/module.modulemap
    framework module BaiduMapAPI_Base {
      umbrella header "BMKBaseComponent.h"
      export *
      link "sqlite3.0"
      link "stdc++.6.0.9"
    }
    \EOF

    # 创建Map Module
    rm -rf Verify-SwiftOC3rd/Vendors/BaiduMapAPI_Map.framework/Modules
    mkdir Verify-SwiftOC3rd/Vendors/BaiduMapAPI_Map.framework/Modules
    touch Verify-SwiftOC3rd/Vendors/BaiduMapAPI_Map.framework/Modules/module.modulemap
    cat <<-EOF > Verify-SwiftOC3rd/Vendors/BaiduMapAPI_Map.framework/Modules/module.modulemap
    framework module BaiduMapAPI_Map {
      umbrella header "BMKMapComponent.h"
      export *
      link "sqlite3.0"
      link "stdc++.6.0.9"
    }
    \EOF

  EOF

end

运行结果如下:

image

我将代码上传到了Verify-SwiftOC3rd,欢迎指正

更多详情可以参考我写的一个框架,里面就包含了上述介绍的应用:SwiftX 针对微信,微博,JPush,网络,缓存,常用view,常用Extension,Json数据解析的封装

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 159,716评论 4 364
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 67,558评论 1 294
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 109,431评论 0 244
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 44,127评论 0 209
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 52,511评论 3 287
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 40,692评论 1 222
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 31,915评论 2 313
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 30,664评论 0 202
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 34,412评论 1 246
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 30,616评论 2 245
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 32,105评论 1 260
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 28,424评论 2 254
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 33,098评论 3 238
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 26,096评论 0 8
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 26,869评论 0 197
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 35,748评论 2 276
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 35,641评论 2 271

推荐阅读更多精彩内容