Swifty Framework Development

for pragmatic developers

Xavier Rubio Jansana

 @teknik_tdr
 https://xrubio.com
 https://github.com/xrubioj/

What?

A framework is a collection of...

  • ...code
  • ...assets
  • ...images
  • ...more

Framework !=
static library

  • Dynamic vs static
  • Bundle vs just code

Pros

  • Allows reutilization
  • Favors encapsulation
  • Favors defining boundaries

Cons

  • Harder to maintain
  • Harder to prototype ↔ architect
  • Slower iteration

How?

  • Manual + git submodules...
  • Carthage
  • CocoaPods
  • Swift Package Manager

Manual

  • Completely manual (download or copy) 😐
  • Git submodules
    ⚠️ Detached heads
    ✅ Exact point in time

In both cases, manual integration

Carthage

  • Not centralized
  • Manual steps
  • More control

CocoaPods

  • Well known
  • Automated
  • Less control ("blackbox")

Swift Package Manager

  • New, less support
  • Server projects

CocoaPods 🏆

Preparation

.bash_profile / .zshrc / ...

							export GEM_HOME=$HOME/.gem
							export PATH=$GEM_HOME/bin:$PATH
						
Installing

							$ gem install cocoapods --user-install
						

Basics


						$ pod init
					

						$ pod install
					

						$ pod update
					

						$ pod outdated
					

Podfile


						platform :ios, '9.0'

						target 'MyApp' do
						  use_frameworks!

						  pod 'Alamofire', '~> 4.5.0'

						  target 'MyAppTests' do
						    inherit! :search_paths
						  end
						end
					

Semver

  • PATCH: bugfixes, doesn't add features
  • MINOR: new features, no breaking changes
  • MAJOR: breaking changes

MAJOR.MINOR.PATCH

semver.org

Semver

  • Exact version  0.1
  • Comparators  > 0.1>= 0.1< 0.1<= 0.1
  • Optimistic comparator  ~> 0.1.2~> 0.1

Podfile.lock

  • Allows pinning versions → reproducible builds
  • Add it to the repo
  • Alternatively, add Pods directory
  • Using exact versions in the Podfile is not enough

Making a CocoaPod

Podspec


						$ pod spec create Lipsum

						Specification created at Lipsum.podspec

						$
					

Podspec


						Pod::Spec.new do |s|

						  s.name         = "Lipsum"
						  s.version      = "0.0.1"
						  s.summary      = "Simple Lorem Ipsum generator framework example."
						  s.description  = <<-DESC
						    Simple Lorem Ipsum generator to support the talk Swify Framework Development for
						    pragmatic developers.
						                   DESC

						  s.homepage     = "http://xrubio.com/talks"
						  s.license      = { :type => "MIT", :file => "LICENSE" }
						  s.author       = "Xavier Rubio Jansana"
						  s.social_media_url = "http://twitter.com/teknik_tdr"

						  s.platform     = :ios, "9.0"

						  s.source       = { :git => "https://github.com/xrubioj/swifty-framework-Lipsum.git",
						                     :tag => "#{s.version}" }
						  s.source_files  = "Lipsum", "Lipsum/**/*.{h,m,swift}"

						end
					

Updated Podfile


						platform :ios, '9.0'

						target 'SampleLipsumApp' do
						  use_frameworks!

						  pod 'Lipsum', :path => '../Lipsum'

						  #target 'SampleLipsumAppTests' do
						  #  inherit! :search_paths
						  #end

						end
					

Let's use it!


						$ pod install
						Analyzing dependencies
						Fetching podspec for `Lipsum` from `../Lipsum`
						Downloading dependencies
						Installing Lipsum (0.0.1)
						Generating Pods project
						Integrating client project

						[!] Please close any current Xcode sessions and use
						  `SampleLipsumApp.xcworkspace` for this project from now on.
						Sending stats
						Pod installation complete! There is 1 dependency from the
						  Podfile and 1 total pod installed.
					

						$ open SampleLipsumApp.xcworkspace
					

Hints

  • Remember public
  • Development Pods
  • pod update not needed

Publishing

  • Create framework project
  • Create podspec
  • echo "4.0" > .swift-version
  • pod lib lint
  • Commit and push to repo
  • Tag with version ("0.0.1") and push
  • pod trunk push Lipsum.podspec
    --allow-warnings

New release

  • Run tests
  • Update podspec (version!)
  • pod lib lint
  • Commit and push to repo
  • Tag with new version ("0.0.2") and push
  • pod trunk push Lipsum.podspec
    --allow-warnings

Private Pods

  • Create a git repo
  • Add: pod repo add private-repo https://github.com/xrubioj/swifty-framework-private-repo.git
  • Push Podspec: pod repo push private-repo Lipsum.podspec
  • Update your Podfile with source

Updated Podfile


						platform :ios, '9.0'

						source 'https://github.com/CocoaPods/Specs.git'
						source 'https://github.com/xrubioj/swifty-framework-private-repo.git'

						target 'SampleLipsumApp' do
						  use_frameworks!

						  pod 'Lipsum', '~> 0.0.1'

						  #target 'SampleLipsumAppTests' do
						  #  inherit! :search_paths
						  #end

						end
					

Questions? 🤔

Thanks! 🎉

Xavier Rubio Jansana

 @teknik_tdr
 https://xrubio.com
 https://github.com/xrubioj/

This talk is available at:
https://xrubio.com/talks/talk-swifty-frameworks/

Swifty Framework Development for pragmatic developers