Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
Browse files

Merge pull request #347 from CocoaPods/t-296

Support for `header_dir` attr in subspecs.
  • Loading branch information...
commit 16a324a7aebbbed3fa8619daa739b693f853cc9f 2 parents d4bc737 + f4326c7
@fabiopelosin fabiopelosin authored
View
1  .gitignore
@@ -13,6 +13,7 @@ examples/Pods
examples/**/Pods
examples/RelativePathProject/RelativePathProject/RelativePathProject.xcodeproj
spec/fixtures/banana-lib
+spec/fixtures/chameleon
spec/fixtures/integration/Headers/
/concatenated.*
spec/fixtures/mercurial-repo/.hg/*cache
View
2  Rakefile
@@ -145,7 +145,7 @@ namespace :gem do
# Update the last version in CocoaPods-version.yml
specs_branch = '0.6'
- Dir.chdir ('../Specs') do
+ Dir.chdir('../Specs') do
puts Dir.pwd
sh "git checkout #{specs_branch}"
sh "git pull"
View
2  lib/cocoapods/command/spec.rb
@@ -406,7 +406,7 @@ def process_xcode_build_output(output)
def file_patterns_errors
messages = []
messages << "The sources did not match any file" if !@spec.source_files.empty? && @pod.source_files.empty?
- messages << "The resources did not match any file" if !@spec.resources.empty? && @pod.resources.empty?
+ messages << "The resources did not match any file" if !@spec.resources.empty? && @pod.resource_files.empty?
messages << "The preserve_paths did not match any file" if !@spec.preserve_paths.empty? && @pod.preserve_paths.empty?
messages << "The exclude_header_search_paths did not match any file" if !@spec.exclude_header_search_paths.empty? && @pod.headers_excluded_from_search_paths.empty?
messages
View
2  lib/cocoapods/installer.rb
@@ -29,7 +29,7 @@ def project
pods.each do |pod|
# Add all source files to the project grouped by pod
group = @project.add_pod_group(pod.name)
- pod.source_files.each do |path|
+ pod.relative_source_files.each do |path|
group.files.new('path' => path.to_s)
end
end
View
4 lib/cocoapods/installer/target_installer.rb
@@ -20,12 +20,12 @@ def xcconfig
end
def copy_resources_script_for(pods)
- @copy_resources_script ||= Generator::CopyResourcesScript.new(pods.map { |p| p.resources }.flatten)
+ @copy_resources_script ||= Generator::CopyResourcesScript.new(pods.map { |p| p.relative_resource_files }.flatten)
end
def bridge_support_generator_for(pods, sandbox)
Generator::BridgeSupport.new(pods.map do |pod|
- pod.header_files.map { |header| sandbox.root + header }
+ pod.relative_header_files.map { |header| sandbox.root + header }
end.flatten)
end
View
187 lib/cocoapods/local_pod.rb
@@ -13,10 +13,13 @@ module Pod
# safely cleaned by the pod.
#
# @example
- #
# pod = LocalPod.new 'RestKit/Networking'
# pod.add_specification 'RestKit/UI'
#
+ # @note
+ # Unless otherwise specified in the name of the method the {LocalPod}
+ # returns absolute paths.
+ #
class LocalPod
# @return [Specification] The specification that describes the pod.
@@ -140,6 +143,7 @@ def implode
#
def clean
clean_paths.each { |path| FileUtils.rm_rf(path) }
+ @cleaned = true
end
# Finds the absolute paths, including hidden ones, of the files
@@ -148,7 +152,7 @@ def clean
# @return [Array<Strings>] The paths that can be deleted.
#
def clean_paths
- cached_used_paths = used_paths.map{ |path| path.to_s }
+ cached_used_paths = used_files
files = Dir.glob(root + "**/*", File::FNM_DOTMATCH)
files.reject! do |candidate|
@@ -159,51 +163,77 @@ def clean_paths
files
end
- # @return [Array<Pathname>] The relative path of the files used by the pod.
+ # @return [Array<String>] The absolute path of the files used by the pod.
#
- def used_paths
- files = [ source_files(false),
- resources(false),
- preserve_paths,
- readme_file,
- license_file,
- prefix_header_file ]
+ def used_files
+ files = [ source_files, resource_files, preserve_files, readme_file, license_file, prefix_header_file ]
files.compact!
files.flatten!
+ files.map!{ |path| path.to_s }
files
end
# @!group Files
- # @param (see #source_files_by_spec)
- #
# @return [Array<Pathname>] The paths of the source files.
#
- def source_files(relative = true)
- chained_expanded_paths(:source_files, :glob => '*.{h,m,mm,c,cpp}', :relative_to_sandbox => relative)
+ def source_files
+ source_files_by_spec.values.flatten
end
- # Finds the source files that every activated {Specification} requires.
+ # @return [Array<Pathname>] The *relative* paths of the source files.
#
- # @param [Boolean] relative Whether the paths should be returned relative
- # to the sandbox.
+ def relative_source_files
+ source_files.map{ |p| p.relative_path_from(@sandbox.root) }
+ end
+
+ # Finds the source files that every activated {Specification} requires.
#
# @note If the same file is required by two specifications the one at the
# higher level in the inheritance chain wins.
#
+ # @return [Hash{Specification => Array<Pathname>}] The files grouped by
+ # {Specification}.
+ #
+ def source_files_by_spec
+ options = {:glob => '*.{h,m,mm,c,cpp}'}
+ paths_by_spec(:source_files, options)
+ end
+
# @return [Array<Pathname>] The paths of the header files.
#
def header_files
- source_files.select { |f| f.extname == '.h' }
+ header_files_by_spec.values.flatten
+ end
+
+ # @return [Array<Pathname>] The *relative* paths of the source files.
+ #
+ def relative_header_files
+ header_files.map{ |p| p.relative_path_from(@sandbox.root) }
end
# @return [Hash{Specification => Array<Pathname>}] The paths of the header
# files grouped by {Specification}.
#
+ def header_files_by_spec
+ result = {}
+ source_files_by_spec.each do |spec, paths|
+ headers = paths.select { |f| f.extname == '.h' }
+ result[spec] = headers unless headers.empty?
+ end
+ result
+ end
+
# @return [Array<Pathname>] The paths of the resources.
#
- def resources(relative = true)
- chained_expanded_paths(:resources, :relative_to_sandbox => relative)
+ def resource_files
+ paths_by_spec(:resources).values.flatten
+ end
+
+ # @return [Array<Pathname>] The *relative* paths of the resources.
+ #
+ def relative_resource_files
+ resource_files.map{ |p| p.relative_path_from(@sandbox.root) }
end
# @return [Pathname] The absolute path of the prefix header file
@@ -215,11 +245,15 @@ def prefix_header_file
# @return [Array<Pathname>] The absolute paths of the files of the pod
# that should be preserved.
#
- def preserve_paths
- chained_expanded_paths(:preserve_paths) + expanded_paths(%w[ *.podspec notice* NOTICE* CREDITS* ])
+ def preserve_files
+ paths = paths_by_spec(:preserve_paths).values
+ paths += expanded_paths(%w[ *.podspec notice* NOTICE* CREDITS* ])
+ paths.compact!
+ paths.uniq!
+ paths
end
- # @return [Pathname] The automatically detected path of the README
+ # @return [Pathname] The automatically detected absolute path of the README
# file.
#
def readme_file
@@ -266,9 +300,16 @@ def xcconfig
# @return [Array<Pathname>] The path of all the public headers of the pod.
#
def all_specs_public_header_files
- #TODO: merge with #221
- specs = top_specification.recursive_subspecs << top_specification
- specs.map { |s| expanded_paths(s.source_files, :glob => '*.{h}') }.compact.flatten.select { |f| f.extname == '.h' }.uniq
+ if @cleaned
+ raise Informative, "The pod is cleaned and cannot compute the all the "\
+ "header files as they might be deleted."
+ end
+
+ all_specs = [ top_specification ] + top_specification.subspecs
+ options = {:glob => '*.{h}'}
+ files = paths_by_spec(:source_files, options, all_specs).values.flatten!
+ headers = files.select { |f| f.extname == '.h' }
+ headers
end
# @!group Target integration
@@ -276,7 +317,8 @@ def all_specs_public_header_files
# @return [void] Copies the pods headers to the sandbox.
#
def link_headers
- copy_header_mappings.each do |namespaced_path, files|
+ @sandbox.add_header_search_path(headers_sandbox)
+ header_mappings.each do |namespaced_path, files|
@sandbox.add_header_files(namespaced_path, files)
end
end
@@ -287,8 +329,9 @@ def link_headers
# @return [void] Adds the pods source files to a given target.
#
def add_to_target(target)
- sources_files_by_specification.each do | spec, files |
+ source_files_by_spec.each do | spec, files |
files.each do |file|
+ file = file.relative_path_from(@sandbox.root)
target.add_source_file(file, nil, spec.compiler_flags.strip)
end
end
@@ -306,7 +349,7 @@ def requires_arc?
# (the files the need to compiled) of the pod.
#
def implementation_files
- source_files.select { |f| f.extname != '.h' }
+ relative_source_files.select { |f| f.extname != '.h' }
end
# @return [Pathname] The path of the pod relative from the sandbox.
@@ -315,63 +358,67 @@ def relative_root
root.relative_path_from(@sandbox.root)
end
+ # @return Hash{Pathname => [Array<Pathname>]} A hash containing the headers
+ # folders as the keys and the the absolute paths of the header files
+ # as the values.
+ #
# @todo this is being overridden in the RestKit 0.9.4 spec, need to do
# something with that, and this method also still exists in Specification.
#
# @todo This is not overridden anymore in specification refactor and the
# code Pod::Specification#copy_header_mapping can be moved here.
- def copy_header_mappings
- search_path_headers = header_files - headers_excluded_from_search_paths
- search_path_headers.inject({}) do |mappings, from|
- from_without_prefix = from.relative_path_from(relative_root)
- to = top_specification.header_dir + top_specification.copy_header_mapping(from_without_prefix)
- (mappings[to.dirname] ||= []) << from
- mappings
+ def header_mappings
+ mappings = {}
+ header_files_by_spec.each do |spec, paths|
+ paths = paths - headers_excluded_from_search_paths
+ paths.each do |from|
+ from_relative = from.relative_path_from(root)
+ to = headers_sandbox + (spec.header_dir) + spec.copy_header_mapping(from_relative)
+ (mappings[to.dirname] ||= []) << from
+ end
end
+ mappings
end
- # Finds the source files that every activate {Specification} requires.
- #
- # @note The paths of the files are relative to the sandbox.
- # @note If the same file is required by two specifications the one at the higher level in the inheritance chain wins.
- #
- # @return [Hash{Specification => Array<Pathname>}] The files grouped by {Specification}.
- #
- def sources_files_by_specification
- files_by_spec = {}
- processed_files = []
- specifications.sort_by { |s| s.name.length }.each do |spec|
- files = []
- expanded_paths(spec.source_files, :glob => '*.{h,m,mm,c,cpp}', :relative_to_sandbox => true).each do | file |
- files << file unless processed_files.include?(file)
- end
- files_by_spec[spec] = files
- processed_files += files
- end
- files_by_spec
+ def headers_sandbox
+ @headers_sandbox ||= Pathname.new(top_specification.name)
end
- # @todo merge with #221
+ # @return [<Pathname>] The relative path of the headers that should not be
+ # included in the linker search paths.
#
def headers_excluded_from_search_paths
- chained_expanded_paths(:exclude_header_search_paths, :glob => '*.h', :relative_to_sandbox => true)
+ options = { :glob => '*.h' }
+ paths = paths_by_spec(:exclude_header_search_paths, options)
+ paths.values.compact.uniq
end
# @!group Paths Patterns
- # Finds all the paths patterns of a each activated specifications and
- # converts them to the actual paths present in the pod.
+ # The paths obtained by resolving the patterns of an attribute
+ # groupped by spec.
#
- # @return [Array<Pathname>] A list of the paths.
+ # @param [Symbol] accessor The accessor to use to obtain the paths patterns.
+ # @param [Hash] options (see #expanded_paths)
#
- def chained_expanded_paths(accessor, options = {})
- specifications.map { |s| expanded_paths(s.send(accessor), options) }.compact.flatten.uniq
+ def paths_by_spec(accessor, options = {}, specs = nil)
+ specs ||= specifications
+ paths_by_spec = {}
+ processed_paths = []
+
+ specs = specs.sort_by { |s| s.name.length }
+ specs.each do |spec|
+ paths = expanded_paths(spec.send(accessor), options)
+ unless paths.empty?
+ paths_by_spec[spec] = paths - processed_paths
+ processed_paths += paths
+ end
+ end
+ paths_by_spec
end
- # The paths obtained by interpolating the patterns of a given attribute
- # collected by spec.
- #
- # @todo implement case insensitive search
+ # Converts patterns of paths to the {Pathname} of the files present in the
+ # pod.
#
# @param [String, FileList, Array<String, Pathname>] patterns
# The patterns to expand.
@@ -379,8 +426,6 @@ def chained_expanded_paths(accessor, options = {})
# The options to used for expanding the paths patterns.
# @option options [String] :glob
# The pattern to use for globing directories.
- # @option options [Boolean] :relative_to_sandbox
- # Whether the paths should be returned relative to the sandbox.
#
# @raise [Informative] If the pod does not exists.
#
@@ -405,11 +450,7 @@ def expanded_paths(patterns, options = {})
end
pattern.glob.map do |file|
- if options[:relative_to_sandbox]
- file.relative_path_from(@sandbox.root)
- else
- file
- end
+ file
end
end.flatten
end
View
10 lib/cocoapods/sandbox.rb
@@ -42,6 +42,16 @@ def header_search_paths
@header_search_paths.uniq.map { |path| "${PODS_ROOT}/#{path}" }
end
+ # Adds an header search path to the sandbox.
+ #
+ # @param path [Pathname] The path tho add.
+ #
+ # @return [void]
+ #
+ def add_header_search_path(path)
+ @header_search_paths << Pathname.new(HEADERS_DIR) + path
+ end
+
def prepare_for_install
headers_root.rmtree if headers_root.exist?
end
View
53 lib/cocoapods/specification.rb
@@ -38,10 +38,18 @@ def initialize(parent = nil, name = nil)
end
# multi-platform attributes
- %w[ source_files resources preserve_paths exclude_header_search_paths frameworks libraries dependencies compiler_flags].each do |attr|
+ %w[ source_files
+ resources
+ preserve_paths
+ exclude_header_search_paths
+ frameworks
+ libraries
+ dependencies
+ compiler_flags ].each do |attr|
instance_variable_set( "@#{attr}", { :ios => [], :osx => [] } )
end
@xcconfig = { :ios => Xcodeproj::Config.new, :osx => Xcodeproj::Config.new }
+ @header_dir = { :ios => nil, :osx => nil }
yield self if block_given?
end
@@ -122,6 +130,7 @@ def initialize(specification, platform)
libraries=
compiler_flags=
deployment_target=
+ header_dir=
dependency }.each do |method|
define_method(method) do |args|
@specification._on_platform(@platform) do
@@ -183,16 +192,10 @@ def available_platforms
top_attr_accessor :license, lambda { |l| ( l.kind_of? String ) ? { :type => l } : l }
top_attr_accessor :version, lambda { |v| Version.new(v) }
top_attr_accessor :authors, lambda { |a| parse_authors(a) }
- top_attr_accessor :header_mappings_dir, lambda { |file| Pathname.new(file) } # If not provided the headers files are flattened
- top_attr_accessor :prefix_header_file, lambda { |file| Pathname.new(file) }
- top_attr_accessor :prefix_header_contents
top_attr_reader :description, lambda {|instance, ivar| ivar || instance.summary }
top_attr_writer :description
- top_attr_reader :header_dir, lambda {|instance, ivar| ivar || instance.pod_destroot_name }
- top_attr_writer :header_dir, lambda {|dir| Pathname.new(dir) }
-
alias_method :author=, :authors=
def self.parse_authors(*names_and_email_addresses)
@@ -206,6 +209,13 @@ def self.parse_authors(*names_and_email_addresses)
### Attributes **with** multiple platform support
+ # @todo allow for subspecs
+ #
+ top_attr_accessor :header_mappings_dir, lambda { |file| Pathname.new(file) } # If not provided the headers files are flattened
+ top_attr_accessor :prefix_header_file, lambda { |file| Pathname.new(file) }
+ top_attr_accessor :prefix_header_contents
+
+
pltf_chained_attr_accessor :source_files, lambda {|value, current| pattern_list(value) }
pltf_chained_attr_accessor :resources, lambda {|value, current| pattern_list(value) }
pltf_chained_attr_accessor :preserve_paths, lambda {|value, current| pattern_list(value) } # Paths that should not be cleaned
@@ -218,7 +228,28 @@ def self.parse_authors(*names_and_email_addresses)
alias_method :framework=, :frameworks=
alias_method :library=, :libraries=
- platform_attr_writer :xcconfig, lambda {|value, current| current.tap { |c| c.merge!(value) } }
+ # @!method header_dir=
+ #
+ # @abstract The directory where to name space the headers files of
+ # the specification.
+ #
+ # @param [String] The headers directory.
+ #
+ platform_attr_writer :header_dir, lambda { |dir, _| Pathname.new(dir) }
+
+ # @abstract (see #header_dir=)
+ #
+ # @return [Pathname] The headers directory.
+ #
+ # @note If no value is provided it returns an empty {Pathname}.
+ #
+ def header_dir
+ @header_dir[active_platform] || (@parent.header_dir if @parent) || Pathname.new('')
+ end
+
+ # @!method xcconfig=
+ #
+ platform_attr_writer :xcconfig, lambda {|value, current| current.tap { |c| c.merge!(value) } }
def xcconfig
raw_xconfig.dup.
@@ -341,12 +372,6 @@ def pod_destroot
end
end
- def pod_destroot_name
- if root = pod_destroot
- root.basename
- end
- end
-
def self.pattern_list(patterns)
if patterns.is_a?(Array) && (!defined?(Rake) || !patterns.is_a?(Rake::FileList))
patterns
View
BIN  spec/fixtures/chameleon.tar.gz
Binary file not shown
View
373 spec/unit/local_pod_spec.rb
@@ -6,7 +6,8 @@
describe "in general" do
before do
@sandbox = temporary_sandbox
- @pod = Pod::LocalPod.new(fixture_spec('banana-lib/BananaLib.podspec'), @sandbox, Pod::Platform.new(:ios))
+ @spec = fixture_spec('banana-lib/BananaLib.podspec')
+ @pod = Pod::LocalPod.new(@spec, @sandbox, Pod::Platform.new(:ios))
copy_fixture_to_pod('banana-lib', @pod)
end
@@ -31,12 +32,29 @@
end
it 'returns an expanded list of source files, relative to the sandbox root' do
- @pod.source_files.sort.should == [
+ @pod.relative_source_files.sort.should == [
Pathname.new("BananaLib/Classes/Banana.m"),
Pathname.new("BananaLib/Classes/Banana.h")
].sort
end
+ it 'returns the source files groupped by specification' do
+ files = @pod.source_files_by_spec[@pod.specifications.first].sort
+ files.should == [
+ @pod.root + "Classes/Banana.m",
+ @pod.root + "Classes/Banana.h"
+ ].sort
+ end
+
+ it 'returns a list of header files' do
+ @pod.relative_header_files.should == [Pathname.new("BananaLib/Classes/Banana.h")]
+ end
+
+ it 'returns a list of header files by specification' do
+ files = @pod.header_files_by_spec[@pod.specifications.first].sort
+ files.should == [ @pod.root + "Classes/Banana.h" ]
+ end
+
it 'returns an expanded list the files to clean' do
clean_paths = @pod.clean_paths.map { |p| p.to_s.gsub(/.*Pods\/BananaLib/,'') }
clean_paths.should.include "/.git/config"
@@ -46,11 +64,7 @@
end
it 'returns an expanded list of resources, relative to the sandbox root' do
- @pod.resources.should == [Pathname.new("BananaLib/Resources/logo-sidebar.png")]
- end
-
- it 'returns a list of header files' do
- @pod.header_files.should == [Pathname.new("BananaLib/Classes/Banana.h")]
+ @pod.relative_resource_files.should == [Pathname.new("BananaLib/Resources/logo-sidebar.png")]
end
it "can link it's headers into the sandbox" do
@@ -84,172 +98,201 @@
end
end
- describe "with installed source," do
- #before do
- #config.project_pods_root = fixture('integration')
- #podspec = fixture('spec-repos/master/SSZipArchive/0.1.0/SSZipArchive.podspec')
- #@spec = Pod::Specification.from_file(podspec)
- #@destroot = fixture('integration/SSZipArchive')
- #end
-
- xit "returns the list of files that the source_files pattern expand to" do
- files = @destroot.glob('**/*.{h,c,m}')
- files = files.map { |file| file.relative_path_from(config.project_pods_root) }
- @spec.expanded_source_files[:ios].sort.should == files.sort
- end
-
- xit "returns the list of headers" do
- files = @destroot.glob('**/*.h')
- files = files.map { |file| file.relative_path_from(config.project_pods_root) }
- @spec.header_files[:ios].sort.should == files.sort
- end
-
- xit "returns a hash of mappings from the pod's destroot to its header dirs, which by default is just the pod's header dir" do
- @spec.copy_header_mappings[:ios].size.should == 1
- @spec.copy_header_mappings[:ios][Pathname.new('SSZipArchive')].sort.should == %w{
- SSZipArchive.h
- minizip/crypt.h
- minizip/ioapi.h
- minizip/mztools.h
- minizip/unzip.h
- minizip/zip.h
- }.map { |f| Pathname.new("SSZipArchive/#{f}") }.sort
- end
-
- xit "allows for customization of header mappings by overriding copy_header_mapping" do
- def @spec.copy_header_mapping(from)
- Pathname.new('ns') + from.basename
- end
- @spec.copy_header_mappings[:ios].size.should == 1
- @spec.copy_header_mappings[:ios][Pathname.new('SSZipArchive/ns')].sort.should == %w{
- SSZipArchive.h
- minizip/crypt.h
- minizip/ioapi.h
- minizip/mztools.h
- minizip/unzip.h
- minizip/zip.h
- }.map { |f| Pathname.new("SSZipArchive/#{f}") }.sort
- end
-
- xit "returns a hash of mappings with a custom header dir prefix" do
- @spec.header_dir = 'AnotherRoot'
- @spec.copy_header_mappings[:ios][Pathname.new('AnotherRoot')].sort.should == %w{
- SSZipArchive.h
- minizip/crypt.h
- minizip/ioapi.h
- minizip/mztools.h
- minizip/unzip.h
- minizip/zip.h
- }.map { |f| Pathname.new("SSZipArchive/#{f}") }.sort
- end
-
- xit "returns the user header search paths" do
- def @spec.copy_header_mapping(from)
- Pathname.new('ns') + from.basename
- end
- @spec.header_search_paths.should == %w{
- "$(PODS_ROOT)/Headers/SSZipArchive"
- "$(PODS_ROOT)/Headers/SSZipArchive/ns"
- }
- end
+ describe "with installed source and multiple subspecs" do
- xit "returns the user header search paths with a custom header dir prefix" do
- @spec.header_dir = 'AnotherRoot'
- def @spec.copy_header_mapping(from)
- Pathname.new('ns') + from.basename
- end
- @spec.header_search_paths.should == %w{
- "$(PODS_ROOT)/Headers/AnotherRoot"
- "$(PODS_ROOT)/Headers/AnotherRoot/ns"
- }
+ def assert_array_equals(expected, computed)
+ delta1 = computed - expected
+ delta1.should == []
+ delta2 = expected - computed
+ delta2.should == []
end
- xit "returns the list of files that the resources pattern expand to" do
- @spec.expanded_resources.should == {}
- @spec.resource = 'LICEN*'
- @spec.expanded_resources[:ios].map(&:to_s).should == %w{ SSZipArchive/LICENSE }
- @spec.expanded_resources[:osx].map(&:to_s).should == %w{ SSZipArchive/LICENSE }
- @spec.resources = 'LICEN*', 'Readme.*'
- @spec.expanded_resources[:ios].map(&:to_s).should == %w{ SSZipArchive/LICENSE SSZipArchive/Readme.markdown }
- @spec.expanded_resources[:osx].map(&:to_s).should == %w{ SSZipArchive/LICENSE SSZipArchive/Readme.markdown }
- end
- end
-
- describe "regarding multiple subspecs" do
-
before do
- # specification with only some subspecs activated
- # to check that only the needed files are being activated
- # A fixture is needed.
- #
- # specification = Pod::Spec.new do |s|
- # ...
- # s.xcconfig = ...
- # s.compiler_flags = ...
- # s.subspec 's1' do |s1|
- # s1.xcconfig = ...
- # s1.compiler_flags = ...
- # s1.ns.source_files = 's1.{h,m}'
- # end
- #
- # s.subspec 's2' do |s2|
- # s2.ns.source_files = 's2.{h,m}'
- # end
- #
- # Add only s1 to the localPod
- # s1 = specification.subspec_by_name(s1)
- # @pod = Pod::LocalPod.new(s1, @sandbox, Pod::Platform.new(:ios))
- # @pod.add_specification(specification)
- end
-
- xit "returns the subspecs" do
- @pod.subspecs.map{ |s| name }.should == %w[ s1 ]
- end
-
- xit "resolve the source files" do
- @pod.source_files.should == %w[ s1.h s1.m ]
- end
-
- xit "resolve the resources" do
- end
-
- xit "resolve the clean paths" do
- @pod.clean_paths.should == %w[ s2.h s2.m ]
- end
-
- xit "resolves the used files" do
- @pod.used_files.should == %w[ s1.h s1.m README.md ]
- end
-
- xit "resolved the header files" do
- @pod.header_files.should == %w[ s1.h ]
- end
-
- xit "resolves the header files of every subspec" do
- @pod.all_specs_public_header_files.should == %w[ s1.h s2.h ]
- end
-
- xit "merges the xcconfigs" do
- end
-
- xit "adds each file to a target with the compiler flags of its specification" do
- # @pod.add_to_target(target)
- end
-
- xit "can provide the source files of all the subspecs" do
- sources = @pod.all_specs_source_files.map { |p| p.relative_path_from(@sandbox.root).to_s }
- sources.should == %w[ s1.h s1.m s2.h s2.m ]
+ @sandbox = temporary_sandbox
+ subspecs = fixture_spec('chameleon/Chameleon.podspec').subspecs
+ @pod = Pod::LocalPod.new(subspecs[0], @sandbox, Pod::Platform.new(:osx))
+ @pod.add_specification(subspecs[1])
+ copy_fixture_to_pod('chameleon', @pod)
+ end
+
+ it "identifies the top level specification" do
+ @pod.top_specification.name.should == 'Chameleon'
+ end
+
+ it "returns the subspecs" do
+ @pod.specifications.map(&:name).should == %w[ Chameleon/UIKit Chameleon/StoreKit ]
+ end
+
+ it "resolve the source files" do
+ computed = @pod.relative_source_files.map(&:to_s)
+ expected = %w[
+ Chameleon/UIKit/Classes/UIKit.h
+ Chameleon/UIKit/Classes/UIView.h
+ Chameleon/UIKit/Classes/UIWindow.h
+ Chameleon/UIKit/Classes/UIView.m
+ Chameleon/UIKit/Classes/UIWindow.m
+ Chameleon/StoreKit/Classes/SKPayment.h
+ Chameleon/StoreKit/Classes/StoreKit.h
+ Chameleon/StoreKit/Classes/SKPayment.m ]
+
+ assert_array_equals(expected, computed)
+ end
+
+ it "resolve the resources" do
+ @pod.relative_resource_files.map(&:to_s).sort.should == [
+ "Chameleon/UIKit/Resources/<UITabBar> background.png",
+ "Chameleon/UIKit/Resources/<UITabBar> background@2x.png" ]
+ end
+
+ it "resolve the clean paths" do
+ # fake_git serves to check that source control files are deleted
+ expected = %w[
+ /.fake_git
+ /.fake_git/branches
+ /.fake_git/HEAD
+ /.fake_git/index
+ /AddressBookUI
+ /AddressBookUI/AddressBookUI_Prefix.pch
+ /AddressBookUI/Classes
+ /AddressBookUI/Classes/ABUnknownPersonViewController.h
+ /AddressBookUI/Classes/ABUnknownPersonViewController.m
+ /AddressBookUI/Classes/AddressBookUI.h
+ /AssetsLibrary
+ /AssetsLibrary/AssetsLibrary_Prefix.pch
+ /AssetsLibrary/Classes
+ /AssetsLibrary/Classes/ALAsset.h
+ /AssetsLibrary/Classes/ALAsset.m
+ /AssetsLibrary/Classes/ALAssetRepresentation.h
+ /AssetsLibrary/Classes/ALAssetRepresentation.m
+ /AssetsLibrary/Classes/ALAssetsFilter.h
+ /AssetsLibrary/Classes/ALAssetsFilter.m
+ /AssetsLibrary/Classes/ALAssetsGroup.h
+ /AssetsLibrary/Classes/ALAssetsGroup.m
+ /AssetsLibrary/Classes/ALAssetsLibrary.h
+ /AssetsLibrary/Classes/ALAssetsLibrary.m
+ /AssetsLibrary/Classes/AssetsLibrary.h
+ /AVFoundation
+ /AVFoundation/AVFoundation_Prefix.pch
+ /AVFoundation/Classes
+ /AVFoundation/Classes/AVAudioPlayer.h
+ /AVFoundation/Classes/AVAudioPlayer.m
+ /AVFoundation/Classes/AVAudioSession.h
+ /AVFoundation/Classes/AVAudioSession.m
+ /AVFoundation/Classes/AVFoundation.h
+ /MediaPlayer
+ /MediaPlayer/Classes
+ /MediaPlayer/Classes/MediaPlayer.h
+ /MediaPlayer/Classes/MPMediaPlayback.h
+ /MediaPlayer/Classes/MPMoviePlayerController.h
+ /MediaPlayer/Classes/MPMoviePlayerController.m
+ /MediaPlayer/Classes/MPMusicPlayerController.h
+ /MediaPlayer/Classes/MPMusicPlayerController.m
+ /MediaPlayer/Classes/UIInternalMovieView.h
+ /MediaPlayer/Classes/UIInternalMovieView.m
+ /MediaPlayer/MediaPlayer_Prefix.pch
+ /MessageUI
+ /MessageUI/Classes
+ /MessageUI/Classes/MessageUI.h
+ /MessageUI/Classes/MFMailComposeViewController.h
+ /MessageUI/Classes/MFMailComposeViewController.m
+ /MessageUI/MessageUI_Prefix.pch
+ /StoreKit/StoreKit_Prefix.pch
+ /UIKit/UIKit_Prefix.pch
+ ]
+ computed = @pod.clean_paths.each{ |p| p.gsub!(@pod.root.to_s, '') }
+ assert_array_equals(expected, computed)
+ end
+
+ it "resolves the used files" do
+ expected = %w[
+ /UIKit/Classes/UIKit.h
+ /UIKit/Classes/UIView.h
+ /UIKit/Classes/UIWindow.h
+ /UIKit/Classes/UIView.m
+ /UIKit/Classes/UIWindow.m
+ /StoreKit/Classes/SKPayment.h
+ /StoreKit/Classes/StoreKit.h
+ /StoreKit/Classes/SKPayment.m
+ /Chameleon.podspec
+ /README.md
+ /LICENSE
+ ] + [
+ "/UIKit/Resources/<UITabBar> background.png",
+ "/UIKit/Resources/<UITabBar> background@2x.png"
+ ]
+ computed = @pod.used_files.map{ |p| p.gsub!(@pod.root.to_s, '').to_s }
+ assert_array_equals(expected, computed)
+ end
+
+
+ it "resolved the header files" do
+ expected = %w[
+ Chameleon/UIKit/Classes/UIKit.h
+ Chameleon/UIKit/Classes/UIView.h
+ Chameleon/UIKit/Classes/UIWindow.h
+ Chameleon/StoreKit/Classes/SKPayment.h
+ Chameleon/StoreKit/Classes/StoreKit.h ]
+ computed = @pod.relative_header_files.map(&:to_s)
+ assert_array_equals(expected, computed)
+ end
+
+ it "resolves the header files of **every** subspec" do
+ computed = @pod.all_specs_public_header_files.map { |p| p.relative_path_from(@pod.root).to_s }
+ expected = %w[
+ UIKit/Classes/UIKit.h
+ UIKit/Classes/UIView.h
+ UIKit/Classes/UIWindow.h
+ StoreKit/Classes/SKPayment.h
+ StoreKit/Classes/StoreKit.h
+ MessageUI/Classes/MessageUI.h
+ MessageUI/Classes/MFMailComposeViewController.h
+ MediaPlayer/Classes/MediaPlayer.h
+ MediaPlayer/Classes/MPMediaPlayback.h
+ MediaPlayer/Classes/MPMoviePlayerController.h
+ MediaPlayer/Classes/MPMusicPlayerController.h
+ MediaPlayer/Classes/UIInternalMovieView.h
+ AVFoundation/Classes/AVAudioPlayer.h
+ AVFoundation/Classes/AVAudioSession.h
+ AVFoundation/Classes/AVFoundation.h
+ AssetsLibrary/Classes/ALAsset.h
+ AssetsLibrary/Classes/ALAssetRepresentation.h
+ AssetsLibrary/Classes/ALAssetsFilter.h
+ AssetsLibrary/Classes/ALAssetsGroup.h
+ AssetsLibrary/Classes/ALAssetsLibrary.h
+ AssetsLibrary/Classes/AssetsLibrary.h
+ ]
+ assert_array_equals(expected, computed)
+ end
+
+ it "merges the xcconfigs without duplicates" do
+ @pod.xcconfig.should == {
+ "OTHER_LDFLAGS"=>"-framework AppKit -framework Foundation -framework IOKit -framework QTKit -framework QuartzCore -framework SystemConfiguration -framework WebKit" }
+ end
+
+ it "returns a hash of mappings with a custom header dir prefix" do
+ mappings = @pod.send(:header_mappings)
+ mappings = mappings.map do |folder, headers|
+ "#{folder} > #{headers.sort.map{ |p| p.relative_path_from(@pod.root).to_s }.join(' ')}"
+ end
+ mappings.sort.should == [
+ "Chameleon/StoreKit > StoreKit/Classes/SKPayment.h StoreKit/Classes/StoreKit.h",
+ "Chameleon/UIKit > UIKit/Classes/UIKit.h UIKit/Classes/UIView.h UIKit/Classes/UIWindow.h" ]
end
- xit 'can clean the unused files' do
- # copy fixture to another folder
- @pod.clean
- @pod.clean_paths.tap do |paths|
- paths.each do |path|
- path.should.not.exist
- end
+ it "respects the headers excluded from the search paths" do
+ @pod.stubs(:headers_excluded_from_search_paths).returns([@pod.root + 'UIKit/Classes/UIKit.h'])
+ mappings = @pod.send(:header_mappings)
+ mappings = mappings.map do |folder, headers|
+ "#{folder} > #{headers.sort.map{ |p| p.relative_path_from(@pod.root).to_s }.join(' ')}"
end
+ mappings.sort.should == [
+ "Chameleon/StoreKit > StoreKit/Classes/SKPayment.h StoreKit/Classes/StoreKit.h",
+ "Chameleon/UIKit > UIKit/Classes/UIView.h UIKit/Classes/UIWindow.h" ]
end
+ it "includes the sandbox of the pod's headers while linking" do
+ @sandbox.expects(:add_header_search_path).with(Pathname.new('Chameleon'))
+ @pod.link_headers
+ end
end
end
Please sign in to comment.
Something went wrong with that request. Please try again.