Compare commits
34 Commits
fix-NSErro
...
legacy-1.x
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
ce76762788 | ||
|
|
34af92b718 | ||
|
|
638a9f365f | ||
|
|
27f22bbc61 | ||
|
|
74193dbadf | ||
|
|
1fa6186cec | ||
|
|
1f4069726b | ||
|
|
bcc947f620 | ||
|
|
9444a2031d | ||
|
|
1ce256172b | ||
|
|
ba8dfca5e5 | ||
|
|
ae5213b3c8 | ||
|
|
b16f8fafb1 | ||
|
|
3a670faa6e | ||
|
|
fe4f8060c8 | ||
|
|
f45e1c7315 | ||
|
|
a334d73617 | ||
|
|
60974d392e | ||
|
|
723f4ae15e | ||
|
|
a7516ade4a | ||
|
|
c33e02a16b | ||
|
|
e67e0c1db7 | ||
|
|
ee76a2e466 | ||
|
|
86b537cfd9 | ||
|
|
328b707336 | ||
|
|
5b45c74d80 | ||
|
|
1c71e5e397 | ||
|
|
80dfcb2585 | ||
|
|
98b2b52462 | ||
|
|
6022f3440b | ||
|
|
315e2f84b0 | ||
|
|
8467d0fa42 | ||
|
|
3ec110b557 | ||
|
|
e2c022d285 |
1
.gitignore
vendored
1
.gitignore
vendored
@ -1,2 +1,3 @@
|
||||
/Carthage
|
||||
/Cartfile.resolved
|
||||
/Build
|
||||
17
.travis.yml
17
.travis.yml
@ -1,15 +1,6 @@
|
||||
language: objective-c
|
||||
xcode_project: PromiseKit.xcodeproj
|
||||
before_install:
|
||||
- brew update
|
||||
- brew install carthage
|
||||
install: carthage bootstrap --verbose
|
||||
xcode_scheme: [PMKiOS, PMKOSX]
|
||||
xcode_sdk: [iphonesimulator8.3, macosx10.10]
|
||||
|
||||
matrix:
|
||||
exclude:
|
||||
- xcode_scheme: PMKOSX
|
||||
xcode_sdk: iphonesimulator8.3
|
||||
- xcode_scheme: PMKiOS
|
||||
xcode_sdk: macosx10.10
|
||||
xcode_scheme: PMKmacOS
|
||||
osx_image: xcode10.1
|
||||
install: carthage bootstrap --platform Mac
|
||||
script: xcodebuild -scheme PMKmacOS build test
|
||||
|
||||
1
Cartfile.private
Normal file
1
Cartfile.private
Normal file
@ -0,0 +1 @@
|
||||
github "mxcl/OMGHTTPURLRQ" ~> 3.2
|
||||
@ -1 +0,0 @@
|
||||
["data", "hi"]
|
||||
@ -1 +0,0 @@
|
||||
{"data": "hi"}
|
||||
@ -1,3 +0,0 @@
|
||||
#super
|
||||
@invalid
|
||||
!json
|
||||
@ -7,17 +7,15 @@
|
||||
<key>CFBundleExecutable</key>
|
||||
<string>$(EXECUTABLE_NAME)</string>
|
||||
<key>CFBundleIdentifier</key>
|
||||
<string>org.promisekit</string>
|
||||
<string>$(PRODUCT_BUNDLE_IDENTIFIER)</string>
|
||||
<key>CFBundleInfoDictionaryVersion</key>
|
||||
<string>6.0</string>
|
||||
<key>CFBundleName</key>
|
||||
<string>$(PRODUCT_NAME)</string>
|
||||
<key>CFBundlePackageType</key>
|
||||
<string>FMWK</string>
|
||||
<string>$(CFBundlePackageType)</string>
|
||||
<key>CFBundleShortVersionString</key>
|
||||
<string>$(CURRENT_PROJECT_VERSION)</string>
|
||||
<key>CFBundleSignature</key>
|
||||
<string>????</string>
|
||||
<string>1.0</string>
|
||||
<key>CFBundleVersion</key>
|
||||
<string>$(CURRENT_PROJECT_VERSION)</string>
|
||||
<key>NSPrincipalClass</key>
|
||||
|
||||
@ -13,15 +13,19 @@ Pod::Spec.new do |s|
|
||||
s.description = 'UIActionSheet UIAlertView CLLocationManager MFMailComposeViewController ACAccountStore StoreKit SKRequest SKProductRequest blocks'
|
||||
s.social_media_url = 'https://twitter.com/mxcl'
|
||||
s.authors = { 'Max Howell' => 'mxcl@me.com' }
|
||||
s.documentation_url = 'http://promisekit.org/api/'
|
||||
s.documentation_url = 'http://promisekit.org/docs/'
|
||||
s.default_subspecs = 'CALayer', 'NSURLConnection', 'NSNotificationCenter',
|
||||
'UIActionSheet', 'UIAlertView', 'UIViewController', 'UIView',
|
||||
'Pause', 'When', 'Until'
|
||||
s.requires_arc = true
|
||||
|
||||
# CocoaPods requires the root spec to have deployment info even though it should get it from the subspecs
|
||||
s.ios.deployment_target = '6.0' # due to https://github.com/CocoaPods/CocoaPods/issues/1001
|
||||
s.osx.deployment_target = '10.7'
|
||||
s.osx.deployment_target = '10.9'
|
||||
s.watchos.deployment_target = '2.0'
|
||||
s.tvos.deployment_target = '9.0'
|
||||
|
||||
def s.mksubspec name, ios: nil, osx: nil
|
||||
def s.mksubspec name, ios: nil, osx: nil, watchos: nil, tvos: nil
|
||||
prefix = name[0..1]
|
||||
framework = case prefix
|
||||
when 'UI' then 'UIKit'
|
||||
@ -41,75 +45,95 @@ Pod::Spec.new do |s|
|
||||
# this method because CocoaPods insists
|
||||
max = Proc.new do |a, b|
|
||||
split = Proc.new{ |f| f.split('.').map{|s| s.to_i } }
|
||||
[split.call(a), split.call(a)].max.join(".")
|
||||
[split.call(a), split.call(b)].max.join(".")
|
||||
end
|
||||
|
||||
ss.dependency 'PromiseKit/Promise'
|
||||
ss.preserve_paths = 'objc/PromiseKit'
|
||||
ss.preserve_paths = 'Sources/PromiseKit'
|
||||
|
||||
# becuase CocoaPods won't lint if the deployment targets of subspecs
|
||||
# are different to the deployment targets of the root spec we have
|
||||
# to just pretend everything is the same as the root spec :P
|
||||
# https://github.com/CocoaPods/CocoaPods/issues/1987
|
||||
if ios
|
||||
#ss.ios.deployment_target = max.call(ios, self.deployment_target(:ios))
|
||||
ss.ios.deployment_target = deployment_target(:ios)
|
||||
ss.ios.deployment_target = max.call(ios, '6.0') # we have to be at least the same as the deployment target of our Promise subspec
|
||||
end
|
||||
if osx
|
||||
#ss.osx.deployment_target = max.call(osx, self.deployment_target(:osx))
|
||||
ss.osx.deployment_target = deployment_target(:osx)
|
||||
ss.osx.deployment_target = max.call(osx, '10.7') # we have to be at least the same as the deployment target of our Promise subspec
|
||||
end
|
||||
|
||||
if watchos
|
||||
ss.watchos.deployment_target = max.call(watchos, '2.0') # we have to be at least the same as the deployment target of our Promise subspec
|
||||
end
|
||||
if tvos
|
||||
ss.tvos.deployment_target = max.call(tvos, '9.0') # we have to be at least the same as the deployment target of our Promise subspec
|
||||
end
|
||||
|
||||
yield(ss) if block_given?
|
||||
|
||||
ss = if !ios
|
||||
ss.ios.deployment_target = nil
|
||||
ss.osx
|
||||
elsif !osx
|
||||
ss.osx.deployment_target = nil
|
||||
ss.ios
|
||||
else
|
||||
ss
|
||||
end
|
||||
|
||||
ss.framework = framework
|
||||
ss.source_files = (ss.source_files rescue []) + ["objc/#{name}+PromiseKit.h", "objc/#{name}+PromiseKit.m"]
|
||||
ss.xcconfig = { "GCC_PREPROCESSOR_DEFINITIONS" => "$(inherited) PMK_#{name.upcase}=1" }
|
||||
|
||||
operating_systems = method(__method__).parameters.select{ |arg| arg[1] != :name }.map { |arg| arg[1].to_s }
|
||||
|
||||
operating_systems.each do |os_name|
|
||||
os, version = case os_name
|
||||
when 'ios' then [ss.ios, ios]
|
||||
when 'osx' then [ss.osx, osx]
|
||||
when 'watchos' then [ss.watchos, watchos]
|
||||
when 'tvos' then [ss.tvos, tvos]
|
||||
end
|
||||
|
||||
if version
|
||||
os.framework = framework
|
||||
os.source_files = (ss.source_files rescue []) + ["Sources/#{name}+PromiseKit.h", "Sources/#{name}+PromiseKit.m"]
|
||||
os.xcconfig = { "GCC_PREPROCESSOR_DEFINITIONS" => "$(inherited) PMK_#{name.upcase}=1" }
|
||||
else
|
||||
os.deployment_target = nil
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
s.subspec 'Promise' do |ss|
|
||||
ss.source_files = 'objc/PromiseKit.h', 'objc/PMKPromise.m', 'objc/PromiseKit/Promise.h', 'objc/PromiseKit/fwd.h'
|
||||
ss.preserve_paths = 'objc/PromiseKit', 'objc/Private'
|
||||
ss.source_files = 'Sources/PromiseKit.h', 'Sources/PMKPromise.m', 'Sources/PromiseKit/Promise.h', 'Sources/PromiseKit/fwd.h'
|
||||
ss.preserve_paths = 'Sources/PromiseKit', 'Sources/Private'
|
||||
ss.frameworks = 'Foundation'
|
||||
|
||||
ss.ios.deployment_target = '6.0' # due to https://github.com/CocoaPods/CocoaPods/issues/1001
|
||||
ss.osx.deployment_target = '10.7'
|
||||
ss.watchos.deployment_target = '2.0'
|
||||
ss.tvos.deployment_target = '9.0'
|
||||
end
|
||||
|
||||
%w{Pause Until When Join Hang Zalgo}.each do |name|
|
||||
s.subspec(name) do |ss|
|
||||
ss.source_files = "objc/PMKPromise+#{name}.m", "objc/PromiseKit/Promise+#{name}.h"
|
||||
ss.source_files = "Sources/PMKPromise+#{name}.m", "Sources/PromiseKit/Promise+#{name}.h"
|
||||
ss.xcconfig = { "GCC_PREPROCESSOR_DEFINITIONS" => "$(inherited) PMK_#{name.upcase}=1" }
|
||||
ss.preserve_paths = 'objc/PromiseKit'
|
||||
ss.preserve_paths = 'Sources/PromiseKit'
|
||||
ss.dependency 'PromiseKit/When' if name == 'Until'
|
||||
ss.dependency 'PromiseKit/Until' if name == 'Join'
|
||||
ss.dependency 'PromiseKit/Promise'
|
||||
|
||||
ss.ios.deployment_target = '6.0' # due to https://github.com/CocoaPods/CocoaPods/issues/1001
|
||||
ss.watchos.deployment_target = '2.0'
|
||||
ss.tvos.deployment_target = '9.0'
|
||||
|
||||
if name == 'When' || name == 'Until' || name == 'Join'
|
||||
ss.osx.deployment_target = '10.8'
|
||||
else
|
||||
ss.osx.deployment_target = '10.7'
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
s.mksubspec 'ACAccountStore', ios: '6.0', osx: '10.8'
|
||||
s.mksubspec 'AVAudioSession', ios: '7.0'
|
||||
s.mksubspec 'CLGeocoder', ios: '5.0', osx: '10.8'
|
||||
s.mksubspec 'CLGeocoder', ios: '5.0', osx: '10.8', watchos: '2.0', tvos: '9.0'
|
||||
s.mksubspec 'CKContainer', ios: '8.0', osx: '10.10'
|
||||
s.mksubspec 'CKDatabase', ios: '8.0', osx: '10.10'
|
||||
s.mksubspec 'CKDatabase', ios: '8.0', osx: '10.10', tvos: '9.0'
|
||||
s.mksubspec 'CLLocationManager', ios: '2.0', osx: '10.6'
|
||||
s.mksubspec 'MKDirections', ios: '7.0', osx: '10.9'
|
||||
s.mksubspec 'MKMapSnapshotter', ios: '7.0', osx: '10.9'
|
||||
s.mksubspec 'NSFileManager', ios: '2.0', osx: '10.5'
|
||||
s.mksubspec 'NSNotificationCenter', ios: '4.0', osx: '10.6'
|
||||
s.mksubspec 'MKMapSnapshotter', ios: '7.0', osx: '10.9', tvos: '9.0'
|
||||
s.mksubspec 'NSFileManager', ios: '2.0', osx: '10.5', watchos: '2.0', tvos: '9.0'
|
||||
s.mksubspec 'NSNotificationCenter', ios: '4.0', osx: '10.6', watchos: '2.0', tvos: '9.0'
|
||||
s.mksubspec 'NSTask', osx: '10.0'
|
||||
s.mksubspec 'NSURLConnection', ios: '5.0', osx: '10.7' do |ss|
|
||||
ss.dependency "OMGHTTPURLRQ"
|
||||
s.mksubspec 'NSURLConnection', ios: '5.0', osx: '10.9' do |ss|
|
||||
ss.dependency "OMGHTTPURLRQ", "~> 3.2"
|
||||
end
|
||||
s.mksubspec 'SKRequest', ios: '3.0', osx: '10.7'
|
||||
s.mksubspec 'SKRequest', ios: '3.0', osx: '10.7', tvos: '9.0'
|
||||
s.mksubspec 'SLRequest', ios: '6.0', osx: '10.8'
|
||||
s.mksubspec 'UIActionSheet', ios: '2.0'
|
||||
s.mksubspec 'UIAlertView', ios: '2.0'
|
||||
@ -118,46 +142,86 @@ Pod::Spec.new do |s|
|
||||
s.mksubspec 'UIViewController', ios: '5.0' do |ss|
|
||||
ss.ios.weak_frameworks = 'AssetsLibrary'
|
||||
end
|
||||
s.mksubspec 'CALayer', ios: '2.0', osx: '10.5'
|
||||
s.mksubspec 'CALayer', ios: '2.0', osx: '10.5', tvos: '9.0'
|
||||
|
||||
s.subspec 'Accounts' do |ss|
|
||||
ss.dependency 'PromiseKit/ACAccountStore'
|
||||
ss.ios.deployment_target = '6.0'
|
||||
ss.osx.deployment_target = '10.8'
|
||||
ss.watchos.deployment_target = nil
|
||||
ss.tvos.deployment_target = nil
|
||||
end
|
||||
s.subspec 'AVFoundation' do |ss|
|
||||
ss.dependency 'PromiseKit/AVAudioSession'
|
||||
ss.ios.deployment_target = '7.0'
|
||||
ss.watchos.deployment_target = nil
|
||||
ss.tvos.deployment_target = nil
|
||||
ss.osx.deployment_target = nil
|
||||
end
|
||||
s.subspec 'CloudKit' do |ss|
|
||||
ss.dependency 'PromiseKit/CKContainer'
|
||||
ss.dependency 'PromiseKit/CKDatabase'
|
||||
ss.ios.deployment_target = '8.0'
|
||||
ss.osx.deployment_target = '10.10'
|
||||
ss.tvos.deployment_target = '9.0'
|
||||
ss.watchos.deployment_target = nil
|
||||
end
|
||||
s.subspec 'CoreLocation' do |ss|
|
||||
ss.dependency 'PromiseKit/CLGeocoder'
|
||||
ss.dependency 'PromiseKit/CLLocationManager'
|
||||
ss.ios.deployment_target = '5.0' # due to https://github.com/CocoaPods/CocoaPods/issues/1001
|
||||
ss.osx.deployment_target = '10.8'
|
||||
ss.watchos.deployment_target = '2.0'
|
||||
ss.tvos.deployment_target = '9.0'
|
||||
end
|
||||
s.subspec 'Foundation' do |ss|
|
||||
ss.dependency 'PromiseKit/NSFileManager'
|
||||
ss.dependency 'PromiseKit/NSNotificationCenter'
|
||||
ss.dependency 'PromiseKit/NSTask'
|
||||
ss.dependency 'PromiseKit/NSURLConnection'
|
||||
ss.ios.deployment_target = '6.0' # due to https://github.com/CocoaPods/CocoaPods/issues/1001
|
||||
ss.osx.deployment_target = '10.9' # due to OMGHTTPURLRQ
|
||||
ss.watchos.deployment_target = '2.0'
|
||||
ss.tvos.deployment_target = '9.0'
|
||||
end
|
||||
s.subspec 'MapKit' do |ss|
|
||||
ss.dependency 'PromiseKit/MKDirections'
|
||||
ss.dependency 'PromiseKit/MKMapSnapshotter'
|
||||
ss.ios.deployment_target = '7.0' # due to https://github.com/CocoaPods/CocoaPods/issues/1001
|
||||
ss.osx.deployment_target = '10.9'
|
||||
ss.tvos.deployment_target = '9.0'
|
||||
ss.watchos.deployment_target = nil
|
||||
end
|
||||
s.subspec 'Social' do |ss|
|
||||
ss.dependency 'PromiseKit/SLRequest'
|
||||
ss.ios.deployment_target = '6.0' # due to https://github.com/CocoaPods/CocoaPods/issues/1001
|
||||
ss.osx.deployment_target = '10.8'
|
||||
ss.watchos.deployment_target = nil
|
||||
ss.tvos.deployment_target = nil
|
||||
end
|
||||
s.subspec 'StoreKit' do |ss|
|
||||
ss.dependency 'PromiseKit/SKRequest'
|
||||
ss.ios.deployment_target = '6.0' # due to https://github.com/CocoaPods/CocoaPods/issues/1001
|
||||
ss.osx.deployment_target = '10.7'
|
||||
ss.watchos.deployment_target = nil
|
||||
ss.tvos.deployment_target = '9.0'
|
||||
end
|
||||
s.subspec 'UIKit' do |ss|
|
||||
ss.dependency 'PromiseKit/UIActionSheet'
|
||||
ss.dependency 'PromiseKit/UIAlertView'
|
||||
ss.dependency 'PromiseKit/UIView'
|
||||
ss.dependency 'PromiseKit/UIViewController'
|
||||
ss.ios.deployment_target = '6.0' # due to https://github.com/CocoaPods/CocoaPods/issues/1001
|
||||
ss.osx.deployment_target = nil
|
||||
ss.watchos.deployment_target = nil
|
||||
ss.tvos.deployment_target = '9.0'
|
||||
end
|
||||
s.subspec 'QuartzCore' do |ss|
|
||||
ss.dependency 'PromiseKit/CALayer'
|
||||
ss.ios.deployment_target = '6.0' # due to https://github.com/CocoaPods/CocoaPods/issues/1001
|
||||
ss.osx.deployment_target = '10.7'
|
||||
ss.watchos.deployment_target = '2.0'
|
||||
ss.tvos.deployment_target = '9.0'
|
||||
end
|
||||
|
||||
s.subspec 'all' do |ss|
|
||||
@ -177,105 +241,10 @@ Pod::Spec.new do |s|
|
||||
ss.dependency 'PromiseKit/StoreKit'
|
||||
ss.dependency 'PromiseKit/UIKit'
|
||||
ss.dependency 'PromiseKit/QuartzCore'
|
||||
end
|
||||
|
||||
s.subspec 'Swift' do |ss|
|
||||
ss.default_subspecs = 'Foundation', 'UIKit'
|
||||
ss.ios.deployment_target = 8.0
|
||||
ss.osx.deployment_target = 10.9
|
||||
|
||||
ss.subspec 'Promise' do |sss|
|
||||
sss.source_files = %w{Promise when misc constants after race}.map{ |x| "Swift Sources/#{x}.swift" }
|
||||
end
|
||||
|
||||
ss.subspec 'CloudKit' do |sss|
|
||||
sss.dependency 'PromiseKit/Swift/Promise'
|
||||
sss.source_files = 'Swift Sources/CK*.swift'
|
||||
sss.ios.deployment_target = 8.0
|
||||
sss.osx.deployment_target = '10.10'
|
||||
end
|
||||
|
||||
ss.subspec 'UIKit' do |sss|
|
||||
sss.dependency 'PromiseKit/Swift/Promise'
|
||||
sss.ios.source_files = 'Swift Sources/UI*.swift'
|
||||
sss.ios.framework = 'AssetsLibrary'
|
||||
end
|
||||
|
||||
ss.subspec 'CoreLocation' do |sss|
|
||||
sss.dependency 'PromiseKit/Swift/Promise'
|
||||
sss.source_files = 'Swift Sources/CL*.swift'
|
||||
end
|
||||
|
||||
ss.subspec 'MapKit' do |sss|
|
||||
sss.dependency 'PromiseKit/Swift/Promise'
|
||||
sss.source_files = 'Swift Sources/MK*.swift'
|
||||
end
|
||||
|
||||
ss.subspec 'NSJSONFromData' do |sss|
|
||||
sss.dependency 'PromiseKit/Swift/Promise' # only needs constants in fact
|
||||
sss.source_files = 'Swift Sources/NSJSONFromData.swift'
|
||||
end
|
||||
|
||||
ss.subspec 'Social' do |sss|
|
||||
sss.dependency 'PromiseKit/Swift/Promise'
|
||||
sss.dependency 'PromiseKit/Swift/NSJSONFromData'
|
||||
sss.source_files = Dir['Swift Sources/SL*.swift']
|
||||
end
|
||||
|
||||
ss.subspec 'StoreKit' do |sss|
|
||||
sss.dependency 'PromiseKit/Swift/Promise'
|
||||
sss.source_files = 'Swift Sources/SK*.swift'
|
||||
end
|
||||
|
||||
ss.subspec 'Foundation' do |sss|
|
||||
sss.dependency 'PromiseKit/Swift/Promise'
|
||||
sss.dependency 'PromiseKit/Swift/NSJSONFromData'
|
||||
sss.dependency 'OMGHTTPURLRQ'
|
||||
ios = %w{NSFileManager NSNotificationCenter NSURLConnection}.map{|x| "Swift Sources/#{x}+Promise.swift"}
|
||||
sss.ios.source_files = ios
|
||||
sss.osx.source_files = ios + ['Swift Sources/NSTask+Promise.swift']
|
||||
end
|
||||
|
||||
ss.subspec 'NSNotificationCenter' do |sss|
|
||||
sss.dependency 'PromiseKit/Swift/Promise'
|
||||
sss.source_files = 'Swift Sources/NSNotificationCenter+Promise.swift'
|
||||
end
|
||||
|
||||
ss.subspec 'Accounts' do |sss|
|
||||
sss.dependency 'PromiseKit/Swift/Promise'
|
||||
sss.source_files = "Swift Sources/AC*.swift"
|
||||
end
|
||||
|
||||
ss.subspec 'AVFoundation' do |sss|
|
||||
sss.dependency 'PromiseKit/Swift/Promise'
|
||||
sss.ios.source_files = "Swift Sources/AV*.swift"
|
||||
end
|
||||
|
||||
ss.subspec 'all' do |sss|
|
||||
sss.dependency 'PromiseKit/Swift/CloudKit'
|
||||
sss.dependency 'PromiseKit/Swift/CoreLocation'
|
||||
sss.dependency 'PromiseKit/Swift/Foundation'
|
||||
sss.dependency 'PromiseKit/Swift/MapKit'
|
||||
sss.dependency 'PromiseKit/Swift/Social'
|
||||
sss.dependency 'PromiseKit/Swift/StoreKit'
|
||||
sss.dependency 'PromiseKit/Swift/UIKit'
|
||||
end
|
||||
ss.ios.deployment_target = '8.0' # due to https://github.com/CocoaPods/CocoaPods/issues/1001
|
||||
ss.osx.deployment_target = '10.10'
|
||||
ss.watchos.deployment_target = '2.0'
|
||||
ss.tvos.deployment_target = '9.0'
|
||||
end
|
||||
|
||||
#### deprecated
|
||||
|
||||
s.subspec 'SKProductsRequest' do |ss|
|
||||
# ss.deprecated_in_favor_of = 'PromiseKit/SKRequest'
|
||||
ss.dependency 'PromiseKit/SKRequest'
|
||||
ss.preserve_paths = 'objc/deprecated'
|
||||
ss.source_files = 'objc/deprecated/SKProductsRequest+PromiseKit.h'
|
||||
end
|
||||
|
||||
s.subspec 'base' do |ss| # deprecated
|
||||
# ss.deprecated_in_favor_of = 'PromiseKit/Promise'
|
||||
ss.dependency 'PromiseKit/Promise'
|
||||
ss.dependency 'PromiseKit/When'
|
||||
ss.dependency 'PromiseKit/Until'
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@ -0,0 +1,8 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
||||
<plist version="1.0">
|
||||
<dict>
|
||||
<key>IDEDidComputeMac32BitWarning</key>
|
||||
<true/>
|
||||
</dict>
|
||||
</plist>
|
||||
@ -1,6 +1,6 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<Scheme
|
||||
LastUpgradeVersion = "0630"
|
||||
LastUpgradeVersion = "0930"
|
||||
version = "1.3">
|
||||
<BuildAction
|
||||
parallelizeBuildables = "YES"
|
||||
@ -14,68 +14,38 @@
|
||||
buildForAnalyzing = "YES">
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "639339731ABCF32B00B7AAA9"
|
||||
BlueprintIdentifier = "63A2EE431D51267E003BED41"
|
||||
BuildableName = "PromiseKit.framework"
|
||||
BlueprintName = "PMKiOS"
|
||||
ReferencedContainer = "container:PromiseKit.xcodeproj">
|
||||
</BuildableReference>
|
||||
</BuildActionEntry>
|
||||
<BuildActionEntry
|
||||
buildForTesting = "YES"
|
||||
buildForRunning = "YES"
|
||||
buildForProfiling = "NO"
|
||||
buildForArchiving = "NO"
|
||||
buildForAnalyzing = "YES">
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6393397D1ABCF32B00B7AAA9"
|
||||
BuildableName = "PMKTests.xctest"
|
||||
BlueprintName = "PMKTests"
|
||||
ReferencedContainer = "container:PromiseKit.xcodeproj">
|
||||
</BuildableReference>
|
||||
</BuildActionEntry>
|
||||
</BuildActionEntries>
|
||||
</BuildAction>
|
||||
<TestAction
|
||||
buildConfiguration = "Debug"
|
||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
||||
shouldUseLaunchSchemeArgsEnv = "YES"
|
||||
buildConfiguration = "Debug">
|
||||
shouldUseLaunchSchemeArgsEnv = "YES">
|
||||
<Testables>
|
||||
<TestableReference
|
||||
skipped = "NO">
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6393397D1ABCF32B00B7AAA9"
|
||||
BuildableName = "PMKTests.xctest"
|
||||
BlueprintName = "PMKTests"
|
||||
ReferencedContainer = "container:PromiseKit.xcodeproj">
|
||||
</BuildableReference>
|
||||
</TestableReference>
|
||||
</Testables>
|
||||
<MacroExpansion>
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "639339731ABCF32B00B7AAA9"
|
||||
BuildableName = "PromiseKit.framework"
|
||||
BlueprintName = "PMKiOS"
|
||||
ReferencedContainer = "container:PromiseKit.xcodeproj">
|
||||
</BuildableReference>
|
||||
</MacroExpansion>
|
||||
<AdditionalOptions>
|
||||
</AdditionalOptions>
|
||||
</TestAction>
|
||||
<LaunchAction
|
||||
buildConfiguration = "Debug"
|
||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
||||
launchStyle = "0"
|
||||
useCustomWorkingDirectory = "NO"
|
||||
buildConfiguration = "Debug"
|
||||
ignoresPersistentStateOnLaunch = "NO"
|
||||
debugDocumentVersioning = "YES"
|
||||
debugServiceExtension = "internal"
|
||||
allowLocationSimulation = "YES">
|
||||
<MacroExpansion>
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "639339731ABCF32B00B7AAA9"
|
||||
BlueprintIdentifier = "63A2EE431D51267E003BED41"
|
||||
BuildableName = "PromiseKit.framework"
|
||||
BlueprintName = "PMKiOS"
|
||||
ReferencedContainer = "container:PromiseKit.xcodeproj">
|
||||
@ -85,15 +55,15 @@
|
||||
</AdditionalOptions>
|
||||
</LaunchAction>
|
||||
<ProfileAction
|
||||
buildConfiguration = "Release"
|
||||
shouldUseLaunchSchemeArgsEnv = "YES"
|
||||
savedToolIdentifier = ""
|
||||
useCustomWorkingDirectory = "NO"
|
||||
buildConfiguration = "Release"
|
||||
debugDocumentVersioning = "YES">
|
||||
<MacroExpansion>
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "639339731ABCF32B00B7AAA9"
|
||||
BlueprintIdentifier = "63A2EE431D51267E003BED41"
|
||||
BuildableName = "PromiseKit.framework"
|
||||
BlueprintName = "PMKiOS"
|
||||
ReferencedContainer = "container:PromiseKit.xcodeproj">
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<Scheme
|
||||
LastUpgradeVersion = "0630"
|
||||
LastUpgradeVersion = "0930"
|
||||
version = "1.3">
|
||||
<BuildAction
|
||||
parallelizeBuildables = "YES"
|
||||
@ -14,60 +14,59 @@
|
||||
buildForAnalyzing = "YES">
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "639339BE1ABCF6AB00B7AAA9"
|
||||
BlueprintIdentifier = "63A2EE261D512252003BED41"
|
||||
BuildableName = "PromiseKit.framework"
|
||||
BlueprintName = "PMKOSX"
|
||||
ReferencedContainer = "container:PromiseKit.xcodeproj">
|
||||
</BuildableReference>
|
||||
</BuildActionEntry>
|
||||
<BuildActionEntry
|
||||
buildForTesting = "YES"
|
||||
buildForRunning = "YES"
|
||||
buildForProfiling = "NO"
|
||||
buildForArchiving = "NO"
|
||||
buildForAnalyzing = "YES">
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "639339C81ABCF6AB00B7AAA9"
|
||||
BuildableName = "PromiseKitTests.xctest"
|
||||
BlueprintName = "PromiseKitTests"
|
||||
BlueprintName = "PMKmacOS"
|
||||
ReferencedContainer = "container:PromiseKit.xcodeproj">
|
||||
</BuildableReference>
|
||||
</BuildActionEntry>
|
||||
</BuildActionEntries>
|
||||
</BuildAction>
|
||||
<TestAction
|
||||
buildConfiguration = "Debug"
|
||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
||||
shouldUseLaunchSchemeArgsEnv = "YES"
|
||||
buildConfiguration = "Debug">
|
||||
shouldUseLaunchSchemeArgsEnv = "YES">
|
||||
<Testables>
|
||||
<TestableReference
|
||||
skipped = "NO">
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "63CB7F6A1D46B20600F4D755"
|
||||
BuildableName = "PMKTests.xctest"
|
||||
BlueprintName = "PMKTests"
|
||||
ReferencedContainer = "container:PromiseKit.xcodeproj">
|
||||
</BuildableReference>
|
||||
</TestableReference>
|
||||
</Testables>
|
||||
<MacroExpansion>
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "639339BE1ABCF6AB00B7AAA9"
|
||||
BlueprintIdentifier = "63A2EE261D512252003BED41"
|
||||
BuildableName = "PromiseKit.framework"
|
||||
BlueprintName = "PMKOSX"
|
||||
BlueprintName = "PMKmacOS"
|
||||
ReferencedContainer = "container:PromiseKit.xcodeproj">
|
||||
</BuildableReference>
|
||||
</MacroExpansion>
|
||||
<AdditionalOptions>
|
||||
</AdditionalOptions>
|
||||
</TestAction>
|
||||
<LaunchAction
|
||||
buildConfiguration = "Debug"
|
||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
||||
launchStyle = "0"
|
||||
useCustomWorkingDirectory = "NO"
|
||||
buildConfiguration = "Debug"
|
||||
ignoresPersistentStateOnLaunch = "NO"
|
||||
debugDocumentVersioning = "YES"
|
||||
debugServiceExtension = "internal"
|
||||
allowLocationSimulation = "YES">
|
||||
<MacroExpansion>
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "639339BE1ABCF6AB00B7AAA9"
|
||||
BlueprintIdentifier = "63A2EE261D512252003BED41"
|
||||
BuildableName = "PromiseKit.framework"
|
||||
BlueprintName = "PMKOSX"
|
||||
BlueprintName = "PMKmacOS"
|
||||
ReferencedContainer = "container:PromiseKit.xcodeproj">
|
||||
</BuildableReference>
|
||||
</MacroExpansion>
|
||||
@ -75,17 +74,17 @@
|
||||
</AdditionalOptions>
|
||||
</LaunchAction>
|
||||
<ProfileAction
|
||||
buildConfiguration = "Release"
|
||||
shouldUseLaunchSchemeArgsEnv = "YES"
|
||||
savedToolIdentifier = ""
|
||||
useCustomWorkingDirectory = "NO"
|
||||
buildConfiguration = "Release"
|
||||
debugDocumentVersioning = "YES">
|
||||
<MacroExpansion>
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "639339BE1ABCF6AB00B7AAA9"
|
||||
BlueprintIdentifier = "63A2EE261D512252003BED41"
|
||||
BuildableName = "PromiseKit.framework"
|
||||
BlueprintName = "PMKOSX"
|
||||
BlueprintName = "PMKmacOS"
|
||||
ReferencedContainer = "container:PromiseKit.xcodeproj">
|
||||
</BuildableReference>
|
||||
</MacroExpansion>
|
||||
@ -2,26 +2,15 @@
|
||||
|
||||
Modern development is highly asynchronous: isn’t it about time iOS developers had tools that made programming asynchronously powerful, easy and delightful?
|
||||
|
||||
# How To Get Started
|
||||
|
||||
* Read PromiseKit’s [comprehensive learning guide](http://promisekit.org/introduction).
|
||||
* Read the [API documentation](http://cocoadocs.org/docsets/PromiseKit/).
|
||||
* [Integrate](http://promisekit.org/getting-started) promises into your existing projects.
|
||||
|
||||
## How To Get Started… Quickly
|
||||
# Getting Started
|
||||
|
||||
```ruby
|
||||
# CocoaPods
|
||||
pod "PromiseKit" # Objective-C PromiseKit
|
||||
pod "PromiseKit/Promise" # Just PMKPromise, none of the categories
|
||||
|
||||
pod "PromiseKit/Swift" # Swift PromiseKit
|
||||
pod "PromiseKit/Swift/Promise" # Just Promise, none of the categories
|
||||
|
||||
# Carthage
|
||||
github "mxcl/PromiseKit" # Swift PromiseKit
|
||||
pod "PromiseKit ~> 1.7"
|
||||
```
|
||||
|
||||
* Read PromiseKit’s [comprehensive learning guide](http://promisekit.org/introduction).
|
||||
|
||||
# Donations
|
||||
|
||||
PromiseKit is hundreds of hours of work almost completely by just me: [Max Howell](https://twitter.com/mxcl). I thoroughly enjoyed making PromiseKit, but nevertheless if you have found it useful then your bitcoin will give me a warm fuzzy feeling from my head right down to my toes: 1JDbV5zuym3jFw4kBCc5Z758maUD8e4dKR.
|
||||
|
||||
@ -30,7 +30,7 @@
|
||||
|
||||
@see requestAccessToAccountsWithType:options:completion:
|
||||
*/
|
||||
- (PMKPromise *)requestAccessToAccountsWithType:(ACAccountType *)type options:(NSDictionary *)options;
|
||||
- (PMKPromise *)requestAccessToAccountsWithType:(ACAccountType *)accountType options:(NSDictionary *)options;
|
||||
|
||||
/**
|
||||
Renews account credentials when the credentials are no longer valid.
|
||||
@ -1,5 +1,5 @@
|
||||
#import "ACAccountStore+PromiseKit.h"
|
||||
#import "PromiseKit/Promise.h"
|
||||
#import <PromiseKit/Promise.h>
|
||||
|
||||
|
||||
@implementation ACAccountStore (PromiseKit)
|
||||
@ -4,7 +4,7 @@
|
||||
// Created by Matthew Loseke on 6/21/14.
|
||||
//
|
||||
|
||||
#import <AVFoundation/AVAudioSession.h>
|
||||
#import <AVFoundation/AVFoundation.h>
|
||||
#import <PromiseKit/fwd.h>
|
||||
|
||||
/**
|
||||
@ -5,7 +5,7 @@
|
||||
//
|
||||
|
||||
#import "AVAudioSession+PromiseKit.h"
|
||||
#import "PromiseKit/Promise.h"
|
||||
#import <PromiseKit/Promise.h>
|
||||
|
||||
@implementation AVAudioSession (PromiseKit)
|
||||
|
||||
@ -31,7 +31,7 @@
|
||||
-(PMKPromise*) promiseAnimation:(CAAnimation*) animation forKey:(NSString*) key {
|
||||
PMKCAAnimationDelegate* d = [[PMKCAAnimationDelegate alloc] init];
|
||||
PMKRetain(d);
|
||||
animation.delegate = d;
|
||||
animation.delegate = (id) d;
|
||||
[self addAnimation:animation forKey:key];
|
||||
return [PMKPromise new:^(PMKPromiseFulfiller fulfill, PMKPromiseRejecter reject) {
|
||||
d->fullfiller = fulfill;
|
||||
@ -1,6 +1,6 @@
|
||||
#import <CloudKit/CKRecordID.h>
|
||||
#import "CKContainer+PromiseKit.h"
|
||||
#import "PromiseKit/Promise.h"
|
||||
#import <PromiseKit/Promise.h>
|
||||
|
||||
@implementation CKContainer (PromiseKit)
|
||||
|
||||
@ -1,5 +1,5 @@
|
||||
#import "CKDatabase+PromiseKit.h"
|
||||
#import "PromiseKit/Promise.h"
|
||||
#import <PromiseKit/Promise.h>
|
||||
|
||||
@implementation CKDatabase (PromiseKit)
|
||||
|
||||
@ -1,5 +1,5 @@
|
||||
#import "CLGeocoder+PromiseKit.h"
|
||||
#import "PromiseKit/Promise.h"
|
||||
#import <PromiseKit/Promise.h>
|
||||
|
||||
|
||||
@implementation CLGeocoder (PromiseKit)
|
||||
@ -1,7 +1,7 @@
|
||||
#import <CoreLocation/CLLocationManagerDelegate.h>
|
||||
#import "CLLocationManager+PromiseKit.h"
|
||||
#import <objc/runtime.h>
|
||||
#import "PromiseKit/Promise.h"
|
||||
#import <PromiseKit/Promise.h>
|
||||
|
||||
@interface PMKLocationManager : CLLocationManager <CLLocationManagerDelegate>
|
||||
@end
|
||||
@ -1,5 +1,5 @@
|
||||
#import "MKDirections+PromiseKit.h"
|
||||
#import "PromiseKit/Promise.h"
|
||||
#import <PromiseKit/Promise.h>
|
||||
|
||||
|
||||
@implementation MKDirections (PromiseKit)
|
||||
@ -1,5 +1,5 @@
|
||||
#import "MKMapSnapshotter+PromiseKit.h"
|
||||
#import "PromiseKit/Promise.h"
|
||||
#import <PromiseKit/Promise.h>
|
||||
|
||||
@implementation MKMapSnapshotter (PromiseKit)
|
||||
|
||||
@ -1,5 +1,5 @@
|
||||
#import "NSFileManager+PromiseKit.h"
|
||||
#import "PromiseKit/Promise.h"
|
||||
#import <PromiseKit/Promise.h>
|
||||
|
||||
|
||||
@implementation NSFileManager (PromiseKit)
|
||||
@ -1,7 +1,7 @@
|
||||
#import <assert.h>
|
||||
#import <Foundation/NSThread.h>
|
||||
#import "NSNotificationCenter+PromiseKit.h"
|
||||
#import "PromiseKit/Promise.h"
|
||||
#import <PromiseKit/Promise.h>
|
||||
|
||||
|
||||
@implementation NSNotificationCenter (PromiseKit)
|
||||
@ -1,4 +1,5 @@
|
||||
#import "PromiseKit/Promise.h"
|
||||
#import <Foundation/Foundation.h>
|
||||
#import <PromiseKit/Promise.h>
|
||||
#import "NSTask+PromiseKit.h"
|
||||
|
||||
@implementation NSTask (PromiseKit)
|
||||
@ -3,6 +3,9 @@
|
||||
#import <Foundation/NSURLRequest.h>
|
||||
#import <PromiseKit/fwd.h>
|
||||
|
||||
#pragma clang diagnostic push
|
||||
#pragma clang diagnostic ignored "-Wdocumentation"
|
||||
|
||||
extern NSString const*const PMKURLErrorFailingURLResponse PMK_DEPRECATED("Use PMKURLErrorFailingURLResponseKey");
|
||||
extern NSString const*const PMKURLErrorFailingData PMK_DEPRECATED("Use PMKURLErrorFailingDataKey");
|
||||
|
||||
@ -141,3 +144,5 @@ extern NSString const*const PMKURLErrorFailingData PMK_DEPRECATED("Use PMKURLErr
|
||||
+ (PMKPromise *)promise:(NSURLRequest *)request;
|
||||
|
||||
@end
|
||||
|
||||
#pragma clang diagnostic pop
|
||||
@ -7,8 +7,7 @@
|
||||
#import <Foundation/NSURLResponse.h>
|
||||
#import "NSURLConnection+PromiseKit.h"
|
||||
#import <OMGHTTPURLRQ/OMGHTTPURLRQ.h>
|
||||
#import <OMGHTTPURLRQ/OMGUserAgent.h>
|
||||
#import "PromiseKit/Promise.h"
|
||||
#import <PromiseKit/Promise.h>
|
||||
|
||||
NSString const*const PMKURLErrorFailingURLResponse = PMKURLErrorFailingURLResponseKey;
|
||||
NSString const*const PMKURLErrorFailingData = PMKURLErrorFailingDataKey;
|
||||
@ -29,27 +28,56 @@ NSString const*const PMKURLErrorFailingData = PMKURLErrorFailingDataKey;
|
||||
} else {
|
||||
urlFormat = [urlFormat description];
|
||||
}
|
||||
return [self promise:[OMGHTTPURLRQ GET:urlFormat:nil]];
|
||||
id err;
|
||||
id rq = [OMGHTTPURLRQ GET:urlFormat:nil error:&err];
|
||||
if (err) {
|
||||
return [PMKPromise promiseWithValue:err];
|
||||
} else {
|
||||
return [self promise:rq];
|
||||
}
|
||||
}
|
||||
|
||||
+ (PMKPromise *)GET:(NSString *)url query:(NSDictionary *)params {
|
||||
return [self promise:[OMGHTTPURLRQ GET:url:params]];
|
||||
id err;
|
||||
id rq = [OMGHTTPURLRQ GET:url:params error:&err];
|
||||
if (err) return [PMKPromise promiseWithValue:err];
|
||||
return [self promise:rq];
|
||||
}
|
||||
|
||||
+ (PMKPromise *)POST:(NSString *)url formURLEncodedParameters:(NSDictionary *)params {
|
||||
return [self promise:[OMGHTTPURLRQ POST:url:params]];
|
||||
id err;
|
||||
id rq = [OMGHTTPURLRQ POST:url:params error:&err];
|
||||
if (err) return [PMKPromise promiseWithValue:err];
|
||||
return [self promise:rq];
|
||||
}
|
||||
|
||||
+ (PMKPromise *)POST:(NSString *)urlString JSON:(NSDictionary *)params {
|
||||
return [self promise:[OMGHTTPURLRQ POST:urlString JSON:params]];
|
||||
id err;
|
||||
id rq = [OMGHTTPURLRQ POST:urlString JSON:params error:&err];
|
||||
if (err) [PMKPromise promiseWithValue:err];
|
||||
return [self promise:rq];
|
||||
}
|
||||
|
||||
+ (PMKPromise *)PUT:(NSString *)url formURLEncodedParameters:(NSDictionary *)params {
|
||||
return [self promise:[OMGHTTPURLRQ PUT:url:params]];
|
||||
id err;
|
||||
id rq = [OMGHTTPURLRQ PUT:url:params error:&err];
|
||||
if (err) [PMKPromise promiseWithValue:err];
|
||||
return [self promise:rq];
|
||||
|
||||
}
|
||||
|
||||
+ (PMKPromise *)DELETE:(NSString *)url formURLEncodedParameters:(NSDictionary *)params {
|
||||
return [self promise:[OMGHTTPURLRQ DELETE:url:params]];
|
||||
id err;
|
||||
id rq = [OMGHTTPURLRQ DELETE:url :params error:&err];
|
||||
if (err) [PMKPromise promiseWithValue:err];
|
||||
return [self promise:rq];
|
||||
}
|
||||
|
||||
+ (PMKPromise *)PATCH:(NSString *)url JSON:(NSDictionary *)params {
|
||||
id err;
|
||||
id rq = [OMGHTTPURLRQ PATCH:url JSON:params error:&err];
|
||||
if (err) [PMKPromise promiseWithValue:err];
|
||||
return [self promise:rq];
|
||||
}
|
||||
|
||||
+ (PMKPromise *)promise:(NSURLRequest *)rq {
|
||||
@ -62,14 +90,14 @@ NSString const*const PMKURLErrorFailingData = PMKURLErrorFailingDataKey;
|
||||
fluff(PMKManifold(responseObject, rsp, data));
|
||||
};
|
||||
PMKPromiseRejecter rejecter = ^(NSError *error){
|
||||
id userInfo = error.userInfo.mutableCopy ?: [NSMutableDictionary new];
|
||||
NSMutableDictionary *userInfo = error.userInfo.mutableCopy ?: [NSMutableDictionary new];
|
||||
if (data) userInfo[PMKURLErrorFailingDataKey] = data;
|
||||
if (rsp) userInfo[PMKURLErrorFailingURLResponseKey] = rsp;
|
||||
error = [NSError errorWithDomain:error.domain code:error.code userInfo:userInfo];
|
||||
rejunk(error);
|
||||
};
|
||||
|
||||
NSStringEncoding (^stringEncoding)() = ^NSStringEncoding{
|
||||
NSStringEncoding (^stringEncoding)(void) = ^NSStringEncoding{
|
||||
id encodingName = [rsp textEncodingName];
|
||||
if (encodingName) {
|
||||
CFStringEncoding encoding = CFStringConvertIANACharSetNameToEncoding((CFStringRef)encodingName);
|
||||
@ -1,4 +1,4 @@
|
||||
#import "PromiseKit/Promise.h"
|
||||
#import <PromiseKit/Promise.h>
|
||||
#import "PromiseKit/Promise+When.h"
|
||||
|
||||
|
||||
@ -11,7 +11,7 @@
|
||||
+ (PMKPromise *)until:(id (^)(void))blockReturningPromises catch:(id)failHandler
|
||||
{
|
||||
return [PMKPromise new:^(PMKPromiseFulfiller fulfill, PMKPromiseRejecter reject){
|
||||
__block void (^block)() = ^{
|
||||
__block void (^block)(void) = ^{
|
||||
PMKPromise *next = [self when:blockReturningPromises()];
|
||||
next.then(^(id o){
|
||||
fulfill(o);
|
||||
@ -11,7 +11,7 @@
|
||||
return [self all:promises];
|
||||
} else if (promises) {
|
||||
return [self all:@[promises]].then(^(NSArray *values){
|
||||
return values[0];
|
||||
return [values objectAtIndex:0];
|
||||
});
|
||||
} else {
|
||||
return [PMKPromise promiseWithValue:nil];
|
||||
@ -32,23 +32,24 @@
|
||||
#define rejecter(key) ^(NSError *err){ \
|
||||
if (newPromise.resolved) \
|
||||
return; \
|
||||
id userInfo = err.userInfo.mutableCopy; \
|
||||
userInfo[PMKFailingPromiseIndexKey] = key; \
|
||||
NSMutableDictionary *userInfo = err.userInfo.mutableCopy; \
|
||||
[userInfo setObject:key forKey:PMKFailingPromiseIndexKey]; \
|
||||
err = [NSError errorWithDomain:err.domain code:err.code userInfo:userInfo]; \
|
||||
rejecter(err); \
|
||||
}
|
||||
|
||||
if ([promises isKindOfClass:[NSDictionary class]])
|
||||
return newPromise = [PMKPromise new:^(PMKPromiseFulfiller fulfiller, PMKPromiseRejecter rejecter){
|
||||
NSDictionary *promiseDictionary = (NSDictionary *) promises;
|
||||
NSMutableDictionary *results = [NSMutableDictionary new];
|
||||
for (id key in promises) {
|
||||
PMKPromise *promise = promises[key];
|
||||
for (id key in promiseDictionary) {
|
||||
PMKPromise *promise = [promiseDictionary objectForKey:key];
|
||||
if (![promise isKindOfClass:[PMKPromise class]])
|
||||
promise = [PMKPromise promiseWithValue:promise];
|
||||
promise.catch(rejecter(key));
|
||||
promise.then(^(id o){
|
||||
if (o)
|
||||
results[key] = o;
|
||||
[results setObject:o forKey:key];
|
||||
if (--count == 0)
|
||||
fulfiller(results);
|
||||
});
|
||||
@ -1,5 +1,5 @@
|
||||
#import <Foundation/NSThread.h>
|
||||
#import "PromiseKit/Promise.h"
|
||||
#import <PromiseKit/Promise.h>
|
||||
#import "PromiseKit/Promise+Zalgo.h"
|
||||
extern id pmk_safely_call_block(id block, id result);
|
||||
|
||||
@ -9,7 +9,7 @@
|
||||
#import <Foundation/NSPointerArray.h>
|
||||
#import <objc/runtime.h>
|
||||
#import "Private/NSMethodSignatureForBlock.m"
|
||||
#import "PromiseKit/Promise.h"
|
||||
#import <PromiseKit/Promise.h>
|
||||
#import <string.h>
|
||||
|
||||
#define IsPromise(o) ([o isKindOfClass:[PMKPromise class]])
|
||||
@ -25,6 +25,7 @@ static const id PMKNull = @"PMKNull";
|
||||
|
||||
|
||||
@interface PMKArray : NSObject
|
||||
- (id)objectAtIndexedSubscript:(NSUInteger)idx;
|
||||
@end
|
||||
|
||||
|
||||
@ -118,19 +119,19 @@ id pmk_safely_call_block(id frock, id result) {
|
||||
case 1: \
|
||||
return ((type(^)(void))frock)(); \
|
||||
case 2: { \
|
||||
const id arg = [result class] == [PMKArray class] ? result[0] : result; \
|
||||
const id arg = [result class] == [PMKArray class] ? ((PMKArray *)result)[0] : result; \
|
||||
return ((type(^)(id))frock)(arg); \
|
||||
} \
|
||||
case 3: { \
|
||||
type (^block)(id, id) = frock; \
|
||||
return [result class] == [PMKArray class] \
|
||||
? block(result[0], result[1]) \
|
||||
? block(((PMKArray *)result)[0], ((PMKArray *)result)[1]) \
|
||||
: block(result, nil); \
|
||||
} \
|
||||
case 4: { \
|
||||
type (^block)(id, id, id) = frock; \
|
||||
return [result class] == [PMKArray class] \
|
||||
? block(result[0], result[1], result[2]) \
|
||||
? block(((PMKArray *)result)[0], ((PMKArray *)result)[1], ((PMKArray *)result)[2]) \
|
||||
: block(result, nil, nil); \
|
||||
} \
|
||||
default: \
|
||||
@ -394,6 +395,10 @@ typedef PMKPromise *(^PMKResolveOnQueueBlock)(dispatch_queue_t, id block);
|
||||
}];
|
||||
}
|
||||
|
||||
- (instancetype)then:(id (^)(id))onFulfilled :(id (^)(id))onRejected {
|
||||
return self.then(onFulfilled).catch(onRejected);
|
||||
}
|
||||
|
||||
+ (PMKPromise *)promiseWithValue:(id)value {
|
||||
PMKPromise *p = [PMKPromise alloc];
|
||||
p->_promiseQueue = PMKCreatePromiseQueue();
|
||||
@ -564,7 +569,7 @@ static void PMKResolve(PMKPromise *this, id result) {
|
||||
if (IsPromise(result))
|
||||
return [(PMKPromise *)result value];
|
||||
if ([result isKindOfClass:[PMKArray class]])
|
||||
return result[0];
|
||||
return ((PMKArray *)result)[0];
|
||||
if (result == PMKNull)
|
||||
return nil;
|
||||
else
|
||||
@ -1,3 +1,6 @@
|
||||
#import <stdlib.h>
|
||||
#import <string.h>
|
||||
|
||||
struct PMKBlockLiteral {
|
||||
void *isa; // initialized to &_NSConcreteStackBlock or &_NSConcreteGlobalBlock
|
||||
int flags;
|
||||
84
Sources/PromiseKit.h
Normal file
84
Sources/PromiseKit.h
Normal file
@ -0,0 +1,84 @@
|
||||
#import <PromiseKit/Promise.h>
|
||||
|
||||
#if __has_include(<PromiseKit/Promise+When.h>)
|
||||
#import <PromiseKit/Promise+When.h>
|
||||
#endif
|
||||
#if __has_include(<PromiseKit/Promise+Until.h>)
|
||||
#import <PromiseKit/Promise+Until.h>
|
||||
#endif
|
||||
#if __has_include(<PromiseKit/Promise+Pause.h>)
|
||||
#import <PromiseKit/Promise+Pause.h>
|
||||
#endif
|
||||
#if __has_include(<PromiseKit/Promise+Join.h>)
|
||||
#import <PromiseKit/Promise+Join.h>
|
||||
#endif
|
||||
#if __has_include(<PromiseKit/Promise+Hang.h>)
|
||||
#import <PromiseKit/Promise+Hang.h>
|
||||
#endif
|
||||
#if __has_include(<PromiseKit/Promise+Zalgo.h>)
|
||||
#import <PromiseKit/Promise+Zalgo.h>
|
||||
#endif
|
||||
|
||||
|
||||
#ifdef PMK_ACACCOUNTSTORE
|
||||
#import <PromiseKit/ACAccountStore+PromiseKit.h>
|
||||
#endif
|
||||
#ifdef PMK_AVAUDIOSESSION
|
||||
#import <PromiseKit/AVAudioSession+PromiseKit.h>
|
||||
#endif
|
||||
#ifdef PMK_CLGEOCODER
|
||||
#import <PromiseKit/CLGeocoder+PromiseKit.h>
|
||||
#endif
|
||||
#ifdef PMK_CLLOCATIONMANAGER
|
||||
#import <PromiseKit/CLLocationManager+PromiseKit.h>
|
||||
#endif
|
||||
#ifdef PMK_CKCONTAINER
|
||||
#import <PromiseKit/CKContainer+PromiseKit.h>
|
||||
#endif
|
||||
#ifdef PMK_CKDATABASE
|
||||
#import <PromiseKit/CKDatabase+PromiseKit.h>
|
||||
#endif
|
||||
#ifdef PMK_MKDIRECTIONS
|
||||
#import <PromiseKit/MKDirections+PromiseKit.h>
|
||||
#endif
|
||||
#ifdef PMK_MKMAPSNAPSHOTTER
|
||||
#import <PromiseKit/MKMapSnapshotter+PromiseKit.h>
|
||||
#endif
|
||||
#ifdef PMK_NSFILEMANAGER
|
||||
#import <PromiseKit/NSFileManager+PromiseKit.h>
|
||||
#endif
|
||||
#ifdef PMK_NSNOTIFICATIONCENTER
|
||||
#import <PromiseKit/NSNotificationCenter+PromiseKit.h>
|
||||
#endif
|
||||
#ifdef PMK_NSTASK
|
||||
#import <PromiseKit/NSTask+PromiseKit.h>
|
||||
#endif
|
||||
#ifdef PMK_NSURLCONNECTION
|
||||
#import <PromiseKit/NSURLConnection+PromiseKit.h>
|
||||
#endif
|
||||
#ifdef PMK_SKREQUEST
|
||||
#import <PromiseKit/SKRequest+PromiseKit.h>
|
||||
#endif
|
||||
#ifdef PMK_SLREQUEST
|
||||
#import <PromiseKit/SLRequest+PromiseKit.h>
|
||||
#endif
|
||||
#ifdef PMK_UIACTIONSHEET
|
||||
#import <PromiseKit/UIActionSheet+PromiseKit.h>
|
||||
#endif
|
||||
#ifdef PMK_UIALERTVIEW
|
||||
#import <PromiseKit/UIAlertView+PromiseKit.h>
|
||||
#endif
|
||||
#ifdef PMK_UIVIEW
|
||||
#import <PromiseKit/UIView+PromiseKit.h>
|
||||
#endif
|
||||
#ifdef PMK_UIVIEWCONTROLLER
|
||||
#import <PromiseKit/UIViewController+PromiseKit.h>
|
||||
#endif
|
||||
|
||||
|
||||
#ifndef PMK_NO_UNPREFIXATION
|
||||
// I used a typedef but it broke the tests, turns out typedefs are new
|
||||
// types that have consequences with isKindOfClass and that
|
||||
// NOTE I will remove this at 1.1
|
||||
typedef PMKPromise Promise PMK_DEPRECATED("Use PMKPromise. Use of Promise is deprecated. This is a typedef, and since it is a typedef, there may be unintended side-effects.");
|
||||
#endif
|
||||
@ -1,6 +1,9 @@
|
||||
#import <PromiseKit/Promise.h>
|
||||
|
||||
|
||||
#pragma clang diagnostic push
|
||||
#pragma clang diagnostic ignored "-Wdocumentation"
|
||||
|
||||
@interface PMKPromise (Until)
|
||||
/**
|
||||
Loops until one or more promises have resolved.
|
||||
@ -16,3 +19,5 @@ An example usage is an app starting up that must get data from the Internet befo
|
||||
+ (PMKPromise *)until:(id(^)(void))blockReturningPromiseOrArrayOfPromises catch:(id)catchHandler;
|
||||
|
||||
@end
|
||||
|
||||
#pragma clang diagnostic pop
|
||||
@ -3,6 +3,9 @@
|
||||
#import <Foundation/NSArray.h>
|
||||
#import <PromiseKit/fwd.h>
|
||||
|
||||
#pragma clang diagnostic push
|
||||
#pragma clang diagnostic ignored "-Wdocumentation"
|
||||
|
||||
/**
|
||||
A promise represents the future value of a task.
|
||||
|
||||
@ -15,7 +18,7 @@
|
||||
@see [PromiseKit `then` Guide](http://promisekit.org/then/)
|
||||
@see [PromiseKit Chaining Guide](http://promisekit.org/chaining/)
|
||||
*/
|
||||
@interface PMKPromise : NSObject
|
||||
@interface PMKPromise<ResultType> : NSObject
|
||||
|
||||
/**
|
||||
The provided block is executed when its receiver is resolved.
|
||||
@ -233,6 +236,15 @@
|
||||
*/
|
||||
+ (instancetype)promiseWithBooleanAdapter:(void (^)(PMKBooleanAdapter adapter))block;
|
||||
|
||||
|
||||
/**
|
||||
This function is provided so Swift can use AnyPromise.
|
||||
|
||||
It is presented as a typical JS-style “thennable”, you can pass `nil`
|
||||
to either parameter and that parameter will be ignored.
|
||||
*/
|
||||
- (instancetype)then:(id (^)(id))onFulfilled :(id (^)(id))onRejected;
|
||||
|
||||
@end
|
||||
|
||||
|
||||
@ -284,3 +296,5 @@ PMKPromise *dispatch_promise_on(dispatch_queue_t q, id block);
|
||||
a safe queue before doing anything else in your handler.
|
||||
*/
|
||||
extern void (^PMKUnhandledErrorHandler)(NSError *);
|
||||
|
||||
#pragma clang diagnostic pop
|
||||
@ -3,9 +3,9 @@
|
||||
@class NSError;
|
||||
@class NSString;
|
||||
@class NSOperationQueue;
|
||||
@class PMKPromise;
|
||||
@class PMKPromise<ResultType>;
|
||||
|
||||
extern NSOperationQueue *PMKOperationQueue();
|
||||
extern NSOperationQueue *PMKOperationQueue(void);
|
||||
|
||||
#define PMK_DEPRECATED(msg) __attribute__((deprecated(msg)))
|
||||
|
||||
@ -5,7 +5,7 @@
|
||||
// Created by Josejulio Martínez on 16/05/14.
|
||||
//
|
||||
|
||||
#import "PromiseKit/Promise.h"
|
||||
#import <PromiseKit/Promise.h>
|
||||
#import <objc/runtime.h>
|
||||
#import "SKRequest+PromiseKit.h"
|
||||
#import <StoreKit/SKProductsRequest.h>
|
||||
@ -4,7 +4,7 @@
|
||||
//
|
||||
//
|
||||
|
||||
#import "PromiseKit/Promise.h"
|
||||
#import <PromiseKit/Promise.h>
|
||||
#import "SLRequest+PromiseKit.h"
|
||||
|
||||
NSString *const SLRequestPromiseKitErrorDomain = PMKErrorDomain;
|
||||
@ -1,5 +1,5 @@
|
||||
#import <objc/runtime.h>
|
||||
#import "PromiseKit/Promise.h"
|
||||
#import <PromiseKit/Promise.h>
|
||||
#import "UIActionSheet+PromiseKit.h"
|
||||
|
||||
|
||||
@ -1,5 +1,5 @@
|
||||
#import <objc/runtime.h>
|
||||
#import "PromiseKit/Promise.h"
|
||||
#import <PromiseKit/Promise.h>
|
||||
#import "UIAlertView+PromiseKit.h"
|
||||
|
||||
|
||||
@ -6,7 +6,7 @@
|
||||
// Copyright (c) 2014年 DeNA. All rights reserved.
|
||||
//
|
||||
|
||||
#import "PromiseKit/Promise.h"
|
||||
#import <PromiseKit/Promise.h>
|
||||
#import "UIView+PromiseKit.h"
|
||||
|
||||
#define PMKMainThreadError [NSError errorWithDomain:PMKErrorDomain code:PMKInvalidUsageError userInfo:@{NSLocalizedDescriptionKey: @"Animation was attempted on a background thread"}]
|
||||
@ -69,6 +69,9 @@
|
||||
#endif
|
||||
|
||||
|
||||
#pragma clang diagnostic push
|
||||
#pragma clang diagnostic ignored "-Wdeprecated-implementations"
|
||||
|
||||
// deprecated
|
||||
|
||||
+ (PMKPromise *)promiseAnimationWithDuration:(NSTimeInterval)duration animations:(void(^)(void))animations {
|
||||
@ -104,4 +107,6 @@
|
||||
|
||||
#endif
|
||||
|
||||
#pragma clang diagnostic pop
|
||||
|
||||
@end
|
||||
@ -1,7 +1,7 @@
|
||||
#import <AssetsLibrary/AssetsLibrary.h>
|
||||
#import <objc/message.h>
|
||||
#import <objc/runtime.h>
|
||||
#import "PromiseKit/Promise.h"
|
||||
#import <PromiseKit/Promise.h>
|
||||
#import <UIKit/UIStoryboardSegue.h>
|
||||
#import <UIKit/UINavigationController.h>
|
||||
#import <UIKit/UIImagePickerController.h>
|
||||
@ -1,83 +0,0 @@
|
||||
import XCTest
|
||||
import PromiseKit
|
||||
|
||||
|
||||
class TestNSURLConnectionPlusPromise: XCTestCase {
|
||||
|
||||
func resource(fn: String, ext: String = "json") -> NSURLRequest {
|
||||
let url = NSBundle(forClass:self.classForCoder).pathForResource(fn, ofType:ext)!
|
||||
return NSURLRequest(URL:NSURL(fileURLWithPath: url)!)
|
||||
}
|
||||
|
||||
var plainText: NSURLRequest { return resource("plain", ext: "text") }
|
||||
var dictionaryJSON: NSURLRequest { return resource("dictionary") }
|
||||
var arrayJSON: NSURLRequest { return resource("array") }
|
||||
|
||||
|
||||
func test_001() {
|
||||
let e1 = expectation()
|
||||
NSURLConnection.promise(dictionaryJSON).then { (json:NSDictionary) -> Int in
|
||||
let hi = json["data"]! as! String
|
||||
XCTAssertEqual(hi as String, "hi")
|
||||
return 1
|
||||
}.catch { _->Int in
|
||||
return 3
|
||||
}.then { (value:Int) -> Void in
|
||||
XCTAssertEqual(value, 1)
|
||||
e1.fulfill()
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func testCorrectlyErrorsWhenExpectingDictionaryAndGettingText() {
|
||||
let e1 = expectation()
|
||||
NSURLConnection.promise(plainText).then { (json:NSDictionary) -> Int in
|
||||
XCTFail()
|
||||
return 1
|
||||
}.catch { (err:NSError) -> Int in
|
||||
XCTAssertEqual(err.domain, NSCocoaErrorDomain as String)
|
||||
XCTAssertEqual(err.code, 3840)
|
||||
return 1234
|
||||
}.then { (value:Int) -> Void in
|
||||
XCTAssertEqual(value, 1234)
|
||||
e1.fulfill()
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func testCorrectlyErrorsWhenExpectingArrayAndGettingDictionary() {
|
||||
let e1 = expectation()
|
||||
NSURLConnection.promise(dictionaryJSON).then { (json:NSArray) -> Int in
|
||||
XCTFail()
|
||||
return 1
|
||||
}.catch { (err:NSError) -> Int in
|
||||
XCTAssertEqual(err.domain, PMKErrorDomain)
|
||||
XCTAssertEqual(err.code, PMKJSONError)
|
||||
XCTAssertEqual(err.userInfo![PMKJSONErrorJSONObjectKey] as! NSDictionary, ["data": "hi"])
|
||||
return 1234
|
||||
}.then { (value:Int) -> Void in
|
||||
XCTAssertEqual(value, 1234)
|
||||
e1.fulfill()
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func testParsesJSONArray() {
|
||||
let e1 = expectation()
|
||||
NSURLConnection.promise(arrayJSON).then { (json:NSArray) -> Int in
|
||||
let hi = json[1] as! String
|
||||
XCTAssertEqual(hi as String, "hi")
|
||||
e1.fulfill()
|
||||
return 1
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func testParsesString() {
|
||||
let e1 = expectation()
|
||||
NSURLConnection.promise(plainText).then{ (txt:String) in
|
||||
e1.fulfill()
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
}
|
||||
@ -1,307 +0,0 @@
|
||||
import XCTest
|
||||
import PromiseKit
|
||||
|
||||
extension XCTestCase {
|
||||
func expectation() -> XCTestExpectation {
|
||||
return expectationWithDescription("")
|
||||
}
|
||||
}
|
||||
|
||||
class TestPromise: XCTestCase {
|
||||
var random:UInt32 = 0
|
||||
|
||||
func sealed() -> Promise<UInt32> {
|
||||
random = arc4random()
|
||||
return Promise(value:random)
|
||||
}
|
||||
|
||||
func unsealed() -> Promise<UInt32> {
|
||||
random = arc4random()
|
||||
|
||||
return Promise<UInt32> { (fulfiller, rejecter) in
|
||||
dispatch_async(dispatch_get_main_queue()){
|
||||
fulfiller(self.random)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func test_hasValue() {
|
||||
let p:Promise<Int> = Promise(value:1)
|
||||
XCTAssertEqual(p.value!, 1)
|
||||
}
|
||||
|
||||
func test_sealedCanThen() {
|
||||
let e1 = expectation()
|
||||
sealed().then { (v:UInt32) -> Void in
|
||||
XCTAssertEqual(v, self.random)
|
||||
e1.fulfill()
|
||||
return
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
|
||||
let e2 = expectation()
|
||||
sealed().then {
|
||||
XCTAssertEqual($0, self.random)
|
||||
}.then {
|
||||
e2.fulfill()
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func test_unsealedCanThen() {
|
||||
let e1 = expectation()
|
||||
unsealed().then { (v:UInt32) -> Void in
|
||||
XCTAssertEqual(v, self.random)
|
||||
e1.fulfill()
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
|
||||
let e2 = expectation()
|
||||
unsealed().then {
|
||||
XCTAssertEqual($0, self.random)
|
||||
}.then {
|
||||
e2.fulfill()
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
|
||||
let e3 = expectation()
|
||||
unsealed().then {
|
||||
XCTAssertEqual($0, self.random)
|
||||
}.then { () -> Void in
|
||||
|
||||
}.then {
|
||||
e3.fulfill()
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func test_returnPromise() {
|
||||
let e1 = expectation()
|
||||
let e2 = expectation()
|
||||
sealed().then { (value) -> Promise<UInt32> in
|
||||
XCTAssertEqual(value, self.random)
|
||||
e1.fulfill()
|
||||
return self.unsealed()
|
||||
}.then { (value) -> Void in
|
||||
XCTAssertEqual(value, self.random)
|
||||
e2.fulfill()
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func test_catch() {
|
||||
let e1 = expectation()
|
||||
Promise<UInt32>{ (_, rejecter) -> Void in
|
||||
rejecter(NSError(domain: PMKErrorDomain, code: 123, userInfo: [:]))
|
||||
}.catch { (err:NSError) -> Void in
|
||||
XCTAssertEqual(err.code, 123)
|
||||
e1.fulfill()
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func test_f_catchAndContinue() {
|
||||
let e1 = expectation()
|
||||
Promise<Int>{ (fulfiller, rejecter) -> Void in
|
||||
rejecter(NSError(domain: PMKErrorDomain, code: 123, userInfo: nil))
|
||||
}.catch { (err:NSError) -> Int in
|
||||
return 123 //TODO return err.code
|
||||
}.then{ (value: Int) -> Void in
|
||||
XCTAssertEqual(value, 123)
|
||||
e1.fulfill()
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func test_finally() {
|
||||
let e1 = expectation()
|
||||
Promise<UInt32>{ (fulfiller, rejecter) in
|
||||
rejecter(NSError(domain: PMKErrorDomain, code: 123, userInfo: [:]))
|
||||
}.finally {
|
||||
e1.fulfill()
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
|
||||
let e2 = expectation()
|
||||
Promise<Int>{ (fulfiller, rejecter) in
|
||||
fulfiller(123)
|
||||
}.finally {
|
||||
e2.fulfill()
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
|
||||
let e3 = expectation()
|
||||
let e4 = expectation()
|
||||
|
||||
Promise<UInt32>{ (fulfiller, rejecter) in
|
||||
rejecter(NSError(domain: PMKErrorDomain, code: 123, userInfo: [:]))
|
||||
}.finally {
|
||||
e3.fulfill()
|
||||
}.catch{ (err:NSError) -> Void in
|
||||
e4.fulfill()
|
||||
XCTAssertEqual(err.domain, PMKErrorDomain)
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
|
||||
let e5 = self.expectationWithDescription("")
|
||||
let e6 = self.expectationWithDescription("")
|
||||
|
||||
Promise<Int>{ (fulfiller, rejecter) in
|
||||
fulfiller(123)
|
||||
}.finally {
|
||||
e5.fulfill()
|
||||
}.then { (value:Int) -> Void in
|
||||
e6.fulfill()
|
||||
XCTAssertEqual(value, 123)
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func test_008_thenOffVoid() {
|
||||
let e1 = expectation()
|
||||
unsealed().then { (value:UInt32) -> Void in
|
||||
return
|
||||
}.then { ()->() in
|
||||
e1.fulfill()
|
||||
return
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func test_008_catchReturnsVoid() {
|
||||
let e1 = expectation()
|
||||
Promise<UInt32>{ (_, rejecter) in
|
||||
rejecter(NSError(domain: PMKErrorDomain, code: 123, userInfo: [:]))
|
||||
}.catch { (err:NSError)->() in
|
||||
XCTAssertEqual(err.code, 123)
|
||||
e1.fulfill()
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func testReturnSelfDoesntInfinitelyRecurseOrSomething() {
|
||||
let e1 = expectation()
|
||||
let p = unsealed()
|
||||
p.then { _-> Promise<UInt32> in
|
||||
return p
|
||||
}.then { _->() in
|
||||
e1.fulfill()
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func testCanCatchOffVoidPromise() {
|
||||
let e1 = expectation()
|
||||
|
||||
let p1 = Promise<Int>{ _, reject in
|
||||
reject(dammy)
|
||||
}
|
||||
let p2 = p1.then{ (number: Int)->Void in
|
||||
let a = "int is \(number)"
|
||||
}
|
||||
let p3 = p2.then{ Void->Void in
|
||||
let a = 1
|
||||
return
|
||||
}
|
||||
|
||||
// Due to Swift finding this situation ambiguous we have to explicitly
|
||||
// tell it which catch to use. As yet I’m not sure of a good solution.
|
||||
// see: https://github.com/mxcl/PromiseKit/issues/56
|
||||
|
||||
let q = dispatch_get_global_queue(0, 0)
|
||||
let catch = p3.catch as (dispatch_queue_t, (err:NSError)->())->()
|
||||
catch(q) { err in
|
||||
e1.fulfill()
|
||||
}
|
||||
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func testZalgo() {
|
||||
var resolved = false
|
||||
Promise(value: 1).thenUnleashZalgo{ x in
|
||||
resolved = true
|
||||
}
|
||||
XCTAssertTrue(resolved)
|
||||
}
|
||||
|
||||
func testWhenAnyObject() {
|
||||
let e1 = expectation()
|
||||
let p1 = Promise(value: 1 as AnyObject)
|
||||
let p2 = Promise(value: 2 as AnyObject)
|
||||
let p3 = Promise(value: 3 as AnyObject)
|
||||
let p4 = Promise(value: 4 as AnyObject)
|
||||
|
||||
when(p1, p2, p3, p4).then { (x: [AnyObject])->() in
|
||||
XCTAssertEqual(x[0] as! Int, 1)
|
||||
XCTAssertEqual(x[1] as! Int, 2)
|
||||
XCTAssertEqual(x[2] as! Int, 3)
|
||||
XCTAssertEqual(x[3] as! Int, 4)
|
||||
XCTAssertEqual(x.count, 4)
|
||||
e1.fulfill()
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func testWhen2() {
|
||||
let e1 = expectation()
|
||||
let p1 = Promise(value: 1)
|
||||
let p2 = Promise(value: "abc")
|
||||
when(p1, p2).then{ (x: Int, y: String)->() in
|
||||
XCTAssertEqual(x, 1)
|
||||
XCTAssertEqual(y, "abc")
|
||||
e1.fulfill()
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func testWhenVoid() {
|
||||
let e1 = expectation()
|
||||
let p1 = Promise(value: 1).then{ x->Void in }
|
||||
let p2 = Promise(value: 2).then{ x->Void in }
|
||||
let p3 = Promise(value: 3).then{ x->Void in }
|
||||
let p4 = Promise(value: 4).then{ x->Void in }
|
||||
|
||||
when([p1, p2, p3, p4]).then{
|
||||
e1.fulfill()
|
||||
}
|
||||
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func testZalgoMore() {
|
||||
let p1 = Promise(value: 1).thenUnleashZalgo{ x->Int in
|
||||
return 2
|
||||
}
|
||||
XCTAssertEqual(p1.value!, 2)
|
||||
|
||||
var x = 0
|
||||
|
||||
let (p2, f, _) = Promise<Int>.defer()
|
||||
p2.thenUnleashZalgo{ _->Void in
|
||||
x = 1
|
||||
}
|
||||
XCTAssertEqual(x, 0)
|
||||
|
||||
f(1)
|
||||
XCTAssertEqual(x, 1)
|
||||
}
|
||||
|
||||
func testRace1() {
|
||||
let ex = expectation()
|
||||
race(after(0.01), after(1.0)).then { (interval: NSTimeInterval, index: Int) -> Void in
|
||||
XCTAssertEqual(index, 0)
|
||||
ex.fulfill()
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func testRace2() {
|
||||
let ex = expectation()
|
||||
race(after(1.0), after(0.01)).then { (interval: NSTimeInterval, index: Int) -> Void in
|
||||
XCTAssertEqual(index, 1)
|
||||
ex.fulfill()
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
}
|
||||
@ -1,73 +0,0 @@
|
||||
import PromiseKit
|
||||
import XCTest
|
||||
|
||||
|
||||
class Test2121: XCTestCase {
|
||||
// "When fulfilled, a promise: must not transition to any other state."
|
||||
|
||||
func test1() {
|
||||
suiteFulfilled(1) { (promise, ee, _)->() in
|
||||
var onFulfilledCalled = false
|
||||
promise.then { a in
|
||||
onFulfilledCalled = true
|
||||
}
|
||||
promise.catch { e->() in
|
||||
XCTAssertFalse(onFulfilledCalled)
|
||||
ee[0].fulfill()
|
||||
}
|
||||
later {
|
||||
ee[0].fulfill()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func test2() {
|
||||
var onFulfilledCalled = false
|
||||
let (promise, fulfiller, rejecter) = Promise<Int>.defer()
|
||||
promise.then{ a -> Void in
|
||||
onFulfilledCalled = true
|
||||
}
|
||||
promise.catch{ e -> Void in
|
||||
XCTAssertFalse(onFulfilledCalled)
|
||||
}
|
||||
fulfiller(dummy)
|
||||
rejecter(dammy)
|
||||
spin()
|
||||
}
|
||||
|
||||
func test3() {
|
||||
var onFulfilledCalled = false
|
||||
let (promise, fulfiller, rejecter) = Promise<Int>.defer()
|
||||
|
||||
promise.then{ a->() in
|
||||
onFulfilledCalled = true;
|
||||
}
|
||||
promise.catch{ e->() in
|
||||
XCTAssertFalse(onFulfilledCalled)
|
||||
}
|
||||
|
||||
later {
|
||||
fulfiller(dummy)
|
||||
rejecter(dammy)
|
||||
}
|
||||
spin()
|
||||
}
|
||||
|
||||
func test4() {
|
||||
var onFulfilledCalled = false
|
||||
let (promise, fulfiller, rejecter) = Promise<Int>.defer()
|
||||
|
||||
promise.then{ a in
|
||||
onFulfilledCalled = true
|
||||
}
|
||||
promise.catch{ e->() in
|
||||
XCTAssertFalse(onFulfilledCalled)
|
||||
}
|
||||
|
||||
fulfiller(dummy)
|
||||
later {
|
||||
rejecter(dammy)
|
||||
}
|
||||
spin()
|
||||
}
|
||||
}
|
||||
@ -1,73 +0,0 @@
|
||||
import PromiseKit
|
||||
import XCTest
|
||||
|
||||
|
||||
class Test2131: XCTestCase {
|
||||
// "When rejected, a promise: must not transition to any other state."
|
||||
|
||||
func test2131_1() {
|
||||
suiteRejected(1) { (promise, exes, _)->() in
|
||||
var onRejectedCalled = false
|
||||
promise.then { _->() in
|
||||
onRejectedCalled = true
|
||||
exes[0].fulfill()
|
||||
}
|
||||
promise.catch { e->() in
|
||||
XCTAssertFalse(onRejectedCalled)
|
||||
}
|
||||
later {
|
||||
exes[0].fulfill()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func test2131_2() {
|
||||
var onRejectedCalled = false
|
||||
let (promise, fulfiller, rejecter) = Promise<Int>.defer()
|
||||
promise.then{ a -> Void in
|
||||
XCTAssertFalse(onRejectedCalled)
|
||||
}
|
||||
promise.catch{ e -> Void in
|
||||
onRejectedCalled = true
|
||||
}
|
||||
fulfiller(dummy)
|
||||
rejecter(dammy)
|
||||
spin()
|
||||
}
|
||||
|
||||
func test2131_3() {
|
||||
var onRejectedCalled = false
|
||||
let (promise, fulfiller, rejecter) = Promise<Int>.defer()
|
||||
|
||||
promise.then{ a->() in
|
||||
XCTAssertFalse(onRejectedCalled)
|
||||
}
|
||||
promise.catch{ e->() in
|
||||
onRejectedCalled = true;
|
||||
}
|
||||
|
||||
later {
|
||||
fulfiller(dummy)
|
||||
rejecter(dammy)
|
||||
}
|
||||
spin()
|
||||
}
|
||||
|
||||
func test2131_4() {
|
||||
var onRejectedCalled = false
|
||||
let (promise, fulfiller, rejecter) = Promise<Int>.defer()
|
||||
|
||||
promise.then{ a in
|
||||
XCTAssertFalse(onRejectedCalled)
|
||||
}
|
||||
promise.catch{ e->() in
|
||||
onRejectedCalled = true
|
||||
}
|
||||
|
||||
fulfiller(dummy)
|
||||
later {
|
||||
rejecter(dammy)
|
||||
}
|
||||
spin()
|
||||
}
|
||||
}
|
||||
@ -1,157 +0,0 @@
|
||||
import PromiseKit
|
||||
import XCTest
|
||||
|
||||
|
||||
class Test222: XCTestCase {
|
||||
// 2.2.2: If `onFulfilled` is a function,
|
||||
|
||||
func test2221() {
|
||||
// 2.2.2.1: it must be called after `promise` is fulfilled,
|
||||
// with `promise`’s fulfillment value as its first argument.
|
||||
|
||||
suiteFulfilled(1) { (promise, exes, sentinel) -> () in
|
||||
promise.then { value->() in
|
||||
XCTAssertEqual(value, sentinel)
|
||||
exes[0].fulfill()
|
||||
return
|
||||
}
|
||||
return
|
||||
}
|
||||
}
|
||||
|
||||
func test2222() {
|
||||
// 2.2.2.2: it must not be called before `promise` is fulfilled
|
||||
|
||||
let e1 = expectationWithDescription("fulfilled after a delay")
|
||||
let (p1, f1, _) = Promise<Int>.defer()
|
||||
var isFulfilled = false
|
||||
|
||||
p1.then { _->() in
|
||||
XCTAssertTrue(isFulfilled)
|
||||
e1.fulfill()
|
||||
}
|
||||
later {
|
||||
f1(dummy)
|
||||
isFulfilled = true
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
|
||||
|
||||
let e2 = expectationWithDescription("never fulfilled")
|
||||
let (p2, f2, _) = Promise<Int>.defer()
|
||||
var onFulfilledCalled = false
|
||||
|
||||
p2.then { _->() in
|
||||
onFulfilledCalled = true
|
||||
e2.fulfill()
|
||||
}
|
||||
later {
|
||||
XCTAssertFalse(onFulfilledCalled)
|
||||
e2.fulfill()
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func test22231() {
|
||||
// 2.2.2.3: it must not be called more than once.
|
||||
// already-fulfilled
|
||||
var timesCalled = 0
|
||||
Promise(value:dummy).then { _->() in
|
||||
XCTAssertEqual(++timesCalled, 1)
|
||||
}
|
||||
}
|
||||
|
||||
func test22232() {
|
||||
// trying to fulfill a pending promise more than once, immediately
|
||||
let (promise, fulfiller, _) = Promise<Int>.defer()
|
||||
var timesCalled = 0
|
||||
promise.then { _->() in
|
||||
XCTAssertEqual(++timesCalled, 1)
|
||||
}
|
||||
fulfiller(dummy)
|
||||
fulfiller(dummy)
|
||||
}
|
||||
|
||||
func test22233() {
|
||||
let (promise, fulfiller, _) = Promise<Int>.defer()
|
||||
var timesCalled = 0
|
||||
let e1 = expectationWithDescription("trying to fulfill a pending promise more than once, delayed")
|
||||
|
||||
promise.then { _->() in
|
||||
XCTAssertEqual(++timesCalled, 1)
|
||||
e1.fulfill()
|
||||
}
|
||||
later {
|
||||
fulfiller(dummy)
|
||||
fulfiller(dummy)
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func test22234() {
|
||||
let (promise, fulfiller, _) = Promise<Int>.defer()
|
||||
var timesCalled = 0
|
||||
let e1 = expectationWithDescription("trying to fulfill a pending promise more than once, immediately then delayed")
|
||||
|
||||
promise.then { _->() in
|
||||
XCTAssertEqual(++timesCalled, 1)
|
||||
e1.fulfill()
|
||||
}
|
||||
fulfiller(dummy)
|
||||
later {
|
||||
fulfiller(dummy)
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func test22235() {
|
||||
let (promise, fulfiller, _) = Promise<Int>.defer()
|
||||
var timesCalled = [0, 0, 0]
|
||||
let desc = "when multiple `then` calls are made, spaced apart in time"
|
||||
let e1 = expectationWithDescription(desc)
|
||||
let e2 = expectationWithDescription(desc)
|
||||
let e3 = expectationWithDescription(desc)
|
||||
|
||||
promise.then { _->() in
|
||||
XCTAssertEqual(++timesCalled[0], 1)
|
||||
e1.fulfill()
|
||||
}
|
||||
later(50.0) {
|
||||
promise.then { _->() in
|
||||
XCTAssertEqual(++timesCalled[1], 1)
|
||||
e2.fulfill()
|
||||
}
|
||||
return
|
||||
}
|
||||
later(100.0) {
|
||||
promise.then { _->() in
|
||||
XCTAssertEqual(++timesCalled[2], 1)
|
||||
e3.fulfill()
|
||||
}
|
||||
return
|
||||
}
|
||||
later(150) {
|
||||
fulfiller(dummy)
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func test2224() {
|
||||
let (promise, fulfiller, _) = Promise<Int>.defer()
|
||||
var timesCalled = [0, 0]
|
||||
let e1 = expectationWithDescription("when `then` is interleaved with fulfillment")
|
||||
|
||||
promise.then { _->() in
|
||||
XCTAssertEqual(++timesCalled[0], 1)
|
||||
}
|
||||
|
||||
fulfiller(dummy)
|
||||
|
||||
promise.then { _->() in
|
||||
XCTAssertEqual(++timesCalled[1], 1)
|
||||
e1.fulfill()
|
||||
}
|
||||
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
}
|
||||
@ -1,156 +0,0 @@
|
||||
import PromiseKit
|
||||
import XCTest
|
||||
|
||||
|
||||
class Test223: XCTestCase {
|
||||
// 2.2.3: If `onRejected` is a function
|
||||
|
||||
func test2231() {
|
||||
// 2.2.3.1: it must be called after `promise` is rejected,
|
||||
// with `promise`’s rejection reason as its first argument
|
||||
suiteRejected(1) { (promise, exes, memo) -> () in
|
||||
promise.catch { error->() in
|
||||
XCTAssertEqual(error, memo)
|
||||
return exes[0].fulfill()
|
||||
}
|
||||
return
|
||||
}
|
||||
}
|
||||
|
||||
func test22321() {
|
||||
// 2.2.3.2: it must not be called before `promise` is fulfilled
|
||||
|
||||
let expectation = expectationWithDescription("rejected after a delay")
|
||||
let (promise, _, rejecter) = Promise<Int>.defer()
|
||||
var isRejected = false
|
||||
|
||||
promise.catch { _->() in
|
||||
XCTAssertTrue(isRejected)
|
||||
expectation.fulfill()
|
||||
}
|
||||
later {
|
||||
rejecter(dammy)
|
||||
isRejected = true
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func test22322() {
|
||||
let expectation = expectationWithDescription("never rejected")
|
||||
let (promise, _, rejecter) = Promise<Int>.defer()
|
||||
var onRejectedCalled = false
|
||||
|
||||
promise.catch { _->() in
|
||||
onRejectedCalled = true
|
||||
expectation.fulfill()
|
||||
}
|
||||
later {
|
||||
XCTAssertFalse(onRejectedCalled)
|
||||
expectation.fulfill()
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func test22331() {
|
||||
// 2.2.3.3: it must not be called more than once.
|
||||
// already-rejected
|
||||
var timesCalled = 0
|
||||
Promise(error:dammy).catch { _->() in
|
||||
XCTAssertEqual(++timesCalled, 1)
|
||||
}
|
||||
}
|
||||
|
||||
func test22332() {
|
||||
// trying to reject a pending promise more than once, immediately
|
||||
let (promise, _, rejecter) = Promise<Int>.defer()
|
||||
var timesCalled = 0
|
||||
promise.catch { _->() in
|
||||
XCTAssertEqual(++timesCalled, 1)
|
||||
}
|
||||
rejecter(dammy)
|
||||
rejecter(dammy)
|
||||
}
|
||||
|
||||
func test22333() {
|
||||
let (promise, _, rejecter) = Promise<Int>.defer()
|
||||
var timesCalled = 0
|
||||
let expectation = expectationWithDescription("trying to reject a pending promise more than once, delayed")
|
||||
|
||||
promise.catch { _->() in
|
||||
XCTAssertEqual(++timesCalled, 1)
|
||||
expectation.fulfill()
|
||||
}
|
||||
later {
|
||||
rejecter(dammy)
|
||||
rejecter(dammy)
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func test22334() {
|
||||
let (promise, _, rejecter) = Promise<Int>.defer()
|
||||
var timesCalled = 0
|
||||
let expectation = expectationWithDescription("trying to fulfill a pending promise more than once, immediately then delayed")
|
||||
|
||||
promise.catch { _->() in
|
||||
XCTAssertEqual(++timesCalled, 1)
|
||||
expectation.fulfill()
|
||||
}
|
||||
rejecter(dammy)
|
||||
later {
|
||||
rejecter(dammy)
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func test22335() {
|
||||
let (promise, _, rejecter) = Promise<Int>.defer()
|
||||
var timesCalled = [0, 0, 0]
|
||||
let desc = "when multiple `then` calls are made, spaced apart in time"
|
||||
let e1 = expectationWithDescription(desc)
|
||||
let e2 = expectationWithDescription(desc)
|
||||
let e3 = expectationWithDescription(desc)
|
||||
|
||||
promise.catch { _->() in
|
||||
XCTAssertEqual(++timesCalled[0], 1)
|
||||
e1.fulfill()
|
||||
}
|
||||
later(50.0) {
|
||||
promise.catch { _->() in
|
||||
XCTAssertEqual(++timesCalled[1], 1)
|
||||
e2.fulfill()
|
||||
}
|
||||
return
|
||||
}
|
||||
later(100.0) {
|
||||
promise.catch { _->() in
|
||||
XCTAssertEqual(++timesCalled[2], 1)
|
||||
e3.fulfill()
|
||||
}
|
||||
return
|
||||
}
|
||||
later(150) {
|
||||
rejecter(dammy)
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func test2234() {
|
||||
let (promise, _, rejecter) = Promise<Int>.defer()
|
||||
var timesCalled = [0, 0]
|
||||
let expectation = expectationWithDescription("when `then` is interleaved with fulfillment")
|
||||
|
||||
promise.catch { _->() in
|
||||
XCTAssertEqual(++timesCalled[0], 1)
|
||||
}
|
||||
|
||||
rejecter(dammy)
|
||||
|
||||
promise.catch { _->() in
|
||||
XCTAssertEqual(++timesCalled[1], 1)
|
||||
expectation.fulfill()
|
||||
}
|
||||
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
}
|
||||
@ -1,173 +0,0 @@
|
||||
import PromiseKit
|
||||
import XCTest
|
||||
|
||||
|
||||
class Test224: XCTestCase {
|
||||
|
||||
// 2.2.4: `onFulfilled` or `onRejected` must not be called until
|
||||
// the execution context stack contains only platform code
|
||||
|
||||
func test2241() {
|
||||
// `then` returns before the promise becomes fulfilled or rejected
|
||||
|
||||
suiteFulfilled(1) { (promise, exes, dummy)->() in
|
||||
var thenHasReturned = false
|
||||
promise.then { _->() in
|
||||
XCTAssert(thenHasReturned)
|
||||
exes[0].fulfill()
|
||||
}
|
||||
thenHasReturned = true
|
||||
}
|
||||
suiteRejected(1) { (promise, exes, memo)->() in
|
||||
var catchHasReturned = false
|
||||
promise.catch { _->() in
|
||||
XCTAssert(catchHasReturned)
|
||||
exes[0].fulfill()
|
||||
}
|
||||
catchHasReturned = true
|
||||
}
|
||||
}
|
||||
|
||||
// Clean-stack execution ordering tests (fulfillment case)
|
||||
|
||||
func test2242_1() {
|
||||
// when `onFulfilled` is added immediately before the promise is fulfilled
|
||||
let (promise, fulfiller, _) = Promise<Int>.defer()
|
||||
var onFulfilledCalled = false
|
||||
|
||||
fulfiller(dummy)
|
||||
promise.then{ _->() in
|
||||
onFulfilledCalled = true
|
||||
}
|
||||
|
||||
XCTAssertFalse(onFulfilledCalled)
|
||||
}
|
||||
|
||||
func test2242_2() {
|
||||
// when one `onFulfilled` is added inside another `onFulfilled`
|
||||
let promise = Promise(value:dummy)
|
||||
var firstOnFulfilledFinished = false
|
||||
let ex = expectation()
|
||||
|
||||
promise.then { _->() in
|
||||
promise.then { _->() in
|
||||
XCTAssert(firstOnFulfilledFinished)
|
||||
ex.fulfill()
|
||||
}
|
||||
firstOnFulfilledFinished = true
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func test2242_3() {
|
||||
// when `onFulfilled` is added inside an `onRejected`
|
||||
let err = NSError(domain: "a", code: 1, userInfo: nil)
|
||||
let resolved = Promise(value:dummy)
|
||||
let rejected = Promise<Int>(error:dammy)
|
||||
|
||||
var firstOnRejectedFinished = false
|
||||
let ex = expectation()
|
||||
|
||||
rejected.catch { _->() in
|
||||
resolved.then { _->() in
|
||||
XCTAssert(firstOnRejectedFinished)
|
||||
ex.fulfill()
|
||||
}
|
||||
firstOnRejectedFinished = true
|
||||
}
|
||||
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func test2242_4() {
|
||||
// when the promise is fulfilled asynchronously
|
||||
let (promise, fulfiller, _) = Promise<Int>.defer()
|
||||
var firstStackFinished = false
|
||||
let ex = expectation()
|
||||
later {
|
||||
fulfiller(dummy)
|
||||
firstStackFinished = true
|
||||
}
|
||||
promise.then { _->() in
|
||||
XCTAssert(firstStackFinished)
|
||||
ex.fulfill()
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
// Clean-stack execution ordering tests (rejection case)
|
||||
|
||||
func test2243() {
|
||||
// when `onRejected` is added immediately before the promise is rejected
|
||||
let (promise, _, rejecter) = Promise<Int>.defer()
|
||||
var onRejectedCalled = false
|
||||
promise.catch{ _->() in
|
||||
onRejectedCalled = true
|
||||
}
|
||||
rejecter(dammy)
|
||||
XCTAssertFalse(onRejectedCalled)
|
||||
}
|
||||
|
||||
func test2244() {
|
||||
// when `onRejected` is added immediately after the promise is rejected
|
||||
let (promise, _, rejecter) = Promise<Int>.defer()
|
||||
var onRejectedCalled = false
|
||||
rejecter(dammy)
|
||||
promise.catch{ _->() in
|
||||
onRejectedCalled = true
|
||||
}
|
||||
XCTAssertFalse(onRejectedCalled)
|
||||
}
|
||||
|
||||
func test2245() {
|
||||
// when `onRejected` is added inside an `onFulfilled`
|
||||
let resolved = Promise(value:dummy)
|
||||
let rejected = Promise<Int>(error:dammy)
|
||||
var firstOnFulfilledFinished = false
|
||||
let ex = expectation()
|
||||
|
||||
resolved.then{ _->() in
|
||||
rejected.catch{ _->() in
|
||||
XCTAssert(firstOnFulfilledFinished)
|
||||
ex.fulfill()
|
||||
}
|
||||
firstOnFulfilledFinished = true
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func test2246() {
|
||||
// when one `onRejected` is added inside another `onRejected`
|
||||
let promise = Promise<Int>(error:dammy)
|
||||
var firstOnRejectedFinished = false
|
||||
let ex = expectation()
|
||||
|
||||
promise.catch{ _->() in
|
||||
promise.catch{ _->() in
|
||||
XCTAssertTrue(firstOnRejectedFinished)
|
||||
ex.fulfill()
|
||||
}
|
||||
firstOnRejectedFinished = true
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func test2247() {
|
||||
// when the promise is rejected asynchronously
|
||||
let (promise, _, rejecter) = Promise<Int>.defer()
|
||||
var firstStackFinished = false
|
||||
let ex = expectation()
|
||||
|
||||
later {
|
||||
rejecter(dammy)
|
||||
firstStackFinished = true
|
||||
}
|
||||
|
||||
promise.catch{ _->() in
|
||||
XCTAssert(firstStackFinished)
|
||||
ex.fulfill()
|
||||
}
|
||||
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
}
|
||||
@ -1,258 +0,0 @@
|
||||
import PromiseKit
|
||||
import XCTest
|
||||
|
||||
|
||||
class Test226: XCTestCase {
|
||||
// 2.2.6: `then` may be called multiple times on the same promise.
|
||||
|
||||
// 2.2.6.1: If/when `promise` is fulfilled, all respective `onFulfilled`
|
||||
// callbacks must execute in the order of their originating calls to `then`.
|
||||
|
||||
func test2261_1() {
|
||||
// multiple boring fulfillment handlers
|
||||
|
||||
suiteFulfilled(4){ (promise, exes, sentinel) -> () in
|
||||
var x = 0
|
||||
promise.then{ _->() in
|
||||
XCTAssertEqual(++x, 1)
|
||||
exes[0].fulfill()
|
||||
}
|
||||
promise.then{ _->() in
|
||||
XCTAssertEqual(++x, 2)
|
||||
exes[1].fulfill()
|
||||
}
|
||||
promise.then{ _->() in
|
||||
XCTAssertEqual(++x, 3)
|
||||
exes[2].fulfill()
|
||||
}
|
||||
promise.then{ (value:Int)->() in
|
||||
XCTAssertEqual(value, sentinel)
|
||||
XCTAssertEqual(x, 3)
|
||||
exes[3].fulfill()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func test2261_2() {
|
||||
// multiple fulfillment handlers, one of which throws
|
||||
|
||||
suiteFulfilled(1) { (promise, ee, sentinel) in
|
||||
var x = 0
|
||||
promise.then{ _->() in
|
||||
XCTAssertEqual(++x, 1)
|
||||
return
|
||||
}
|
||||
promise.then{ _->() in
|
||||
XCTAssertEqual(++x, 2)
|
||||
return
|
||||
}
|
||||
promise.then{ _-> Promise<Int> in
|
||||
XCTAssertEqual(++x, 3)
|
||||
return Promise{ $1(dammy) }
|
||||
}
|
||||
promise.then{ (value:Int)->() in
|
||||
XCTAssertEqual(value, sentinel)
|
||||
XCTAssertEqual(x, 3)
|
||||
ee[0].fulfill()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func test2261_3() {
|
||||
// results in multiple branching chains with their own fulfillment values
|
||||
|
||||
suiteFulfilled(3) { (promise, exes, memo) in
|
||||
let sentinel1 = 671
|
||||
let sentinel2 = 672
|
||||
let sentinel3 = 673
|
||||
|
||||
promise.then { _->Int in
|
||||
return sentinel1
|
||||
}.then { value->() in
|
||||
XCTAssertEqual(sentinel1, value)
|
||||
exes[0].fulfill()
|
||||
}
|
||||
|
||||
promise.then{ _->(Promise<Int>) in
|
||||
return Promise{ $1(NSError(domain:PMKErrorDomain, code:sentinel2, userInfo:nil)) }
|
||||
}.catch { err->() in
|
||||
XCTAssertEqual(err.code, sentinel2)
|
||||
exes[1].fulfill()
|
||||
}
|
||||
|
||||
promise.then{ _->Int in
|
||||
return sentinel3
|
||||
}.then { value->() in
|
||||
XCTAssertEqual(value, sentinel3)
|
||||
exes[2].fulfill()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func test2261_4() {
|
||||
// `onFulfilled` handlers are called in the original order
|
||||
suiteFulfilled(3) { (promise, exes, memo) in
|
||||
var x = 0
|
||||
|
||||
promise.then{ _->() in
|
||||
XCTAssertEqual(x++, 0)
|
||||
exes[0].fulfill()
|
||||
}
|
||||
promise.then{ _->() in
|
||||
XCTAssertEqual(x++, 1)
|
||||
exes[1].fulfill()
|
||||
}
|
||||
promise.then{ _->() in
|
||||
XCTAssertEqual(x++, 2)
|
||||
exes[2].fulfill()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func test2261_5() {
|
||||
// even when one handler is added inside another handler
|
||||
suiteFulfilled(3) { (promise, exes, memo) in
|
||||
var x = 0
|
||||
promise.then{ _->() in
|
||||
XCTAssertEqual(x++, 0)
|
||||
exes[0].fulfill()
|
||||
promise.then{ _->() in
|
||||
XCTAssertEqual(x++, 2)
|
||||
exes[1].fulfill()
|
||||
}
|
||||
}
|
||||
promise.then{ _->() in
|
||||
XCTAssertEqual(x++, 1)
|
||||
exes[2].fulfill()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// 2.2.6.2: If/when `promise` is rejected, all respective `onRejected` callbacks must execute in the order of their originating calls to `then`
|
||||
|
||||
func test2262_1() {
|
||||
// multiple boring rejection handlers
|
||||
|
||||
suiteRejected(4){ (promise, exes, sentinel) -> () in
|
||||
var x = 0
|
||||
promise.catch{ _->() in
|
||||
XCTAssertEqual(++x, 1)
|
||||
exes[0].fulfill()
|
||||
}
|
||||
promise.catch{ _->() in
|
||||
XCTAssertEqual(++x, 2)
|
||||
exes[1].fulfill()
|
||||
}
|
||||
promise.catch{ _->() in
|
||||
XCTAssertEqual(++x, 3)
|
||||
exes[2].fulfill()
|
||||
}
|
||||
promise.catch{ (err:NSError)->() in
|
||||
XCTAssertEqual(err, sentinel)
|
||||
XCTAssertEqual(x, 3)
|
||||
exes[3].fulfill()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func test2262_2() {
|
||||
// multiple rejection handlers, one of which throws
|
||||
|
||||
suiteRejected(1) { (promise, ee, sentinel) in
|
||||
let blah = NSError(domain:PMKErrorDomain, code:923764, userInfo:nil)
|
||||
var x = 0
|
||||
promise.catch{ err->() in
|
||||
XCTAssertEqual(err, sentinel)
|
||||
XCTAssertEqual(++x, 1)
|
||||
return
|
||||
}
|
||||
promise.catch{ err->() in
|
||||
XCTAssertEqual(err, sentinel)
|
||||
XCTAssertEqual(++x, 2)
|
||||
return
|
||||
}
|
||||
promise.catch{ err->Promise<Int> in
|
||||
XCTAssertEqual(err, sentinel)
|
||||
XCTAssertEqual(++x, 3)
|
||||
return Promise<Int>{ $1(blah) }
|
||||
}
|
||||
promise.catch{ err->() in
|
||||
XCTAssertEqual(err, sentinel)
|
||||
XCTAssertEqual(x, 3)
|
||||
ee[0].fulfill()
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
func test2262_3() {
|
||||
// results in multiple branching chains with their own fulfillment values
|
||||
|
||||
suiteRejected(3) { (promise, exes, memo) in
|
||||
let sentinel1 = 671
|
||||
let sentinel2 = 672
|
||||
let sentinel3 = 673
|
||||
|
||||
promise.catch { _->Int in
|
||||
return sentinel1
|
||||
}.then { value->() in
|
||||
XCTAssertEqual(sentinel1, value)
|
||||
exes[0].fulfill()
|
||||
}
|
||||
|
||||
promise.catch{ _->(Promise<Int>) in
|
||||
return Promise{ $1(NSError(domain:PMKErrorDomain, code:sentinel2, userInfo:nil)) }
|
||||
}.catch { err->() in
|
||||
XCTAssertEqual(err.code, sentinel2)
|
||||
exes[1].fulfill()
|
||||
}
|
||||
|
||||
promise.catch{ _->Int in
|
||||
return sentinel3
|
||||
}.then { value->() in
|
||||
XCTAssertEqual(value, sentinel3)
|
||||
exes[2].fulfill()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func test2262_4() {
|
||||
// `onRejected` handlers are called in the original order
|
||||
|
||||
suiteRejected(3) { (promise, exes, memo) in
|
||||
var x = 0
|
||||
|
||||
promise.catch{ _->() in
|
||||
XCTAssertEqual(x++, 0)
|
||||
exes[0].fulfill()
|
||||
}
|
||||
promise.catch{ _->() in
|
||||
XCTAssertEqual(x++, 1)
|
||||
exes[1].fulfill()
|
||||
}
|
||||
promise.catch{ _->() in
|
||||
XCTAssertEqual(x++, 2)
|
||||
exes[2].fulfill()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func test2262_5() {
|
||||
// even when one handler is added inside another handler
|
||||
suiteRejected(3) { (promise, exes, memo) in
|
||||
var x = 0
|
||||
promise.catch{ _->() in
|
||||
XCTAssertEqual(x++, 0)
|
||||
exes[0].fulfill()
|
||||
promise.catch{ _->() in
|
||||
XCTAssertEqual(x++, 2)
|
||||
exes[1].fulfill()
|
||||
}
|
||||
}
|
||||
promise.catch{ _->() in
|
||||
XCTAssertEqual(x++, 1)
|
||||
exes[2].fulfill()
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -1,114 +0,0 @@
|
||||
import PromiseKit
|
||||
import XCTest
|
||||
|
||||
|
||||
class Test232: XCTestCase {
|
||||
|
||||
func testPromiseResolution(factory:()->Promise<Int>, test:(Promise<Int>)->()) {
|
||||
// via return from a fulfilled promise
|
||||
let p1 = Promise(value:dummy).then{ _->Promise<Int> in
|
||||
return factory()
|
||||
}
|
||||
test(p1)
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
|
||||
// via return from a rejected promise
|
||||
let p2 = Promise<Int>(error:dammy).catch{ _->Promise<Int> in
|
||||
return factory()
|
||||
}
|
||||
test(p2)
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
// 2.3.2: If `x` is a promise, adopt its state
|
||||
|
||||
func test2321() {
|
||||
// 2.3.2.1: If `x` is pending, `promise` must remain pending until `x` is fulfilled or rejected.
|
||||
|
||||
testPromiseResolution({
|
||||
return Promise<Int>.defer().promise
|
||||
}, test: { promise in
|
||||
let ex = self.expectation()
|
||||
var wasFulfilled = false
|
||||
var wasRejected = false
|
||||
|
||||
promise.then { foo in
|
||||
wasFulfilled = true
|
||||
}
|
||||
promise.catch { foo in
|
||||
wasRejected = true
|
||||
}
|
||||
later(100){
|
||||
XCTAssertFalse(wasFulfilled)
|
||||
XCTAssertFalse(wasRejected)
|
||||
ex.fulfill()
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
// 2.3.2.2: If/when `x` is fulfilled, fulfill `promise` with the same value.
|
||||
|
||||
func test2322_1() {
|
||||
// `x` is already-fulfilled
|
||||
|
||||
testPromiseResolution({
|
||||
return Promise(value:sentinel)
|
||||
}, test: { promise in
|
||||
let ex = self.expectation()
|
||||
let promise = Promise(value:dummy).then { _-> Promise<Int> in
|
||||
return Promise(value:sentinel)
|
||||
}
|
||||
promise.then { value->() in
|
||||
XCTAssertEqual(value, sentinel)
|
||||
ex.fulfill()
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
func test2322_2() {
|
||||
// `x` is eventually-fulfilled
|
||||
|
||||
testPromiseResolution({
|
||||
let (promise, fulfiller, _) = Promise<Int>.defer()
|
||||
later { fulfiller(sentinel) }
|
||||
return promise
|
||||
}, test: { promise in
|
||||
let ex = self.expectation()
|
||||
promise.then{ value->Void in
|
||||
XCTAssertEqual(value, sentinel)
|
||||
ex.fulfill()
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
// 2.3.2.3: If/when `x` is rejected, reject `promise` with the same reason
|
||||
|
||||
func test2323_1() {
|
||||
// `x` is already-rejected
|
||||
|
||||
testPromiseResolution({
|
||||
return Promise(error:dammy)
|
||||
}, test: { promise in
|
||||
let ex = self.expectation()
|
||||
promise.catch{ error->Void in
|
||||
XCTAssertEqual(error, dammy)
|
||||
ex.fulfill()
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
func test2323_2() {
|
||||
// `x` is eventually-rejected
|
||||
testPromiseResolution({
|
||||
let (promise, _, rejecter) = Promise<Int>.defer()
|
||||
later { rejecter(dammy) }
|
||||
return promise
|
||||
}, test: { promise in
|
||||
let ex = self.expectation()
|
||||
promise.catch{ error->Void in
|
||||
XCTAssertEqual(error, dammy)
|
||||
ex.fulfill()
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
@ -1,54 +0,0 @@
|
||||
import PromiseKit
|
||||
import XCTest
|
||||
|
||||
class Test233: XCTestCase {
|
||||
|
||||
// func testPromiseResolution(xFactory: ()->Promise<Int>, test: (Promise<Int>, XCTestExpectation)->Void) {
|
||||
// // via return from a fulfilled promise
|
||||
// let e1 = expectation()
|
||||
// var p1 = Promise(value:dummy).then { _->Promise<Int> in
|
||||
// return xFactory()
|
||||
// }
|
||||
// test(p1, e1)
|
||||
//
|
||||
// // via return from a rejected promise
|
||||
// let e2 = expectation()
|
||||
// var p2 = Promise(error:dammy).catch { _->Promise<Int> in
|
||||
// return xFactory()
|
||||
// }
|
||||
// test(p2, e2)
|
||||
// }
|
||||
//
|
||||
// // 2.3.3: Otherwise, if `x` is an object or function,
|
||||
// // 2.3.3.1: Let `then` be `x.then`
|
||||
//
|
||||
// func test23311() {
|
||||
// // `x` is an object with null prototype
|
||||
//
|
||||
// var numberOfTimesThenWasRetrieved = null;
|
||||
//
|
||||
// beforeEach(function () {
|
||||
// numberOfTimesThenWasRetrieved = 0;
|
||||
// });
|
||||
//
|
||||
// func xFactory() {
|
||||
// return Object.create(null, {
|
||||
// then: {
|
||||
// get: function () {
|
||||
// ++numberOfTimesThenWasRetrieved;
|
||||
// return function thenMethodForX(onFulfilled) {
|
||||
// onFulfilled();
|
||||
// };
|
||||
// }
|
||||
// }
|
||||
// });
|
||||
// }
|
||||
//
|
||||
// testPromiseResolution(xFactory) { (promise, ex) in
|
||||
// promise.then {
|
||||
// XCTAssertEqual(numberOfTimesThenWasRetrieved, 1)
|
||||
// ex.fulfill()
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
}
|
||||
@ -1,32 +0,0 @@
|
||||
import PromiseKit
|
||||
import XCTest
|
||||
|
||||
|
||||
class Test234: XCTestCase {
|
||||
|
||||
// 2.3.4: If `x` is not an object or function, fulfill `promise` with `x`
|
||||
|
||||
func test234() {
|
||||
suiteFulfilled(1) { (promise1, exes, memo)->Void in
|
||||
let promise2 = promise1.then { (a: Int)->Int in
|
||||
return 1
|
||||
}
|
||||
|
||||
promise2.then { (a: Int)->Void in
|
||||
XCTAssertEqual(a, 1)
|
||||
exes[0].fulfill()
|
||||
}
|
||||
}
|
||||
|
||||
suiteRejected(1) { (promise1, exes, memo)->Void in
|
||||
let promise2 = promise1.catch { (a: NSError)->Int in
|
||||
return 1
|
||||
}
|
||||
|
||||
promise2.then { (a: Int)->Void in
|
||||
XCTAssertEqual(a, 1)
|
||||
exes[0].fulfill()
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -1,24 +0,0 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
||||
<plist version="1.0">
|
||||
<dict>
|
||||
<key>CFBundleDevelopmentRegion</key>
|
||||
<string>en</string>
|
||||
<key>CFBundleExecutable</key>
|
||||
<string>$(EXECUTABLE_NAME)</string>
|
||||
<key>CFBundleIdentifier</key>
|
||||
<string>org.promisekit.Tests</string>
|
||||
<key>CFBundleInfoDictionaryVersion</key>
|
||||
<string>6.0</string>
|
||||
<key>CFBundleName</key>
|
||||
<string>$(PRODUCT_NAME)</string>
|
||||
<key>CFBundlePackageType</key>
|
||||
<string>BNDL</string>
|
||||
<key>CFBundleShortVersionString</key>
|
||||
<string>$(CURRENT_PROJECT_VERSION)</string>
|
||||
<key>CFBundleSignature</key>
|
||||
<string>????</string>
|
||||
<key>CFBundleVersion</key>
|
||||
<string>1</string>
|
||||
</dict>
|
||||
</plist>
|
||||
@ -1,83 +0,0 @@
|
||||
import PromiseKit
|
||||
import XCTest
|
||||
|
||||
// we fulfill with this when we don't intend to test against it
|
||||
let dummy = 123
|
||||
|
||||
// we reject with this when we don't intend to test against it
|
||||
let dammy = NSError(domain: PMKErrorDomain, code: dummy, userInfo: nil)
|
||||
|
||||
// a sentinel fulfillment value to test for with strict equality
|
||||
var sentinel = 456
|
||||
|
||||
func later(block: ()->()) {
|
||||
later(50, block)
|
||||
}
|
||||
func later(timeout:Double, block: ()->()) {
|
||||
let ticks = Double(NSEC_PER_SEC) / (timeout * 1000.0)
|
||||
dispatch_after(dispatch_time(DISPATCH_TIME_NOW, Int64(ticks)), dispatch_get_main_queue(), block)
|
||||
}
|
||||
|
||||
func spin() {
|
||||
NSRunLoop.mainRunLoop().runUntilDate(NSDate(timeIntervalSinceNow: 0.1))
|
||||
}
|
||||
|
||||
|
||||
extension XCTestCase {
|
||||
func suiteFulfilled(numberOfExpectations:Int, test:(Promise<Int>, [XCTestExpectation!], Int)->Void) {
|
||||
|
||||
func e(desc: String) -> [XCTestExpectation!] {
|
||||
return [Int](1...numberOfExpectations).map{ self.expectationWithDescription("\(desc) (\($0))") }
|
||||
}
|
||||
|
||||
let v1 = Int(rand())
|
||||
let e1 = e("already-fulfilled")
|
||||
test(Promise(value:v1), e1, v1)
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
|
||||
let d2 = Promise<Int>.defer()
|
||||
let v2 = Int(rand())
|
||||
let e2 = e("immediately-fulfilled")
|
||||
test(d2.promise, e2, v2)
|
||||
d2.fulfill(v2)
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
|
||||
let d3 = Promise<Int>.defer()
|
||||
let v3 = Int(rand())
|
||||
let e3 = e("eventually-fulfilled")
|
||||
later {
|
||||
test(d3.promise, e3, v3)
|
||||
d3.fulfill(v3)
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
|
||||
func suiteRejected(numberOfExpectations:Int, test:(Promise<Int>, [XCTestExpectation!], NSError)->Void) {
|
||||
|
||||
func e(desc: String) -> [XCTestExpectation!] {
|
||||
return [Int](1...numberOfExpectations).map{ self.expectationWithDescription("\(desc) (\($0))") }
|
||||
}
|
||||
|
||||
let v1 = NSError(domain:PMKErrorDomain, code:Int(rand()), userInfo:nil)
|
||||
let e1 = e("already-fulfilled")
|
||||
|
||||
test(Promise(error:v1), e1, v1)
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
|
||||
let e2 = e("immediately-rejected")
|
||||
let d2 = Promise<Int>.defer()
|
||||
let v2 = NSError(domain:PMKErrorDomain, code:Int(rand()), userInfo:nil)
|
||||
test(d2.promise, e2, v2)
|
||||
d2.reject(v2)
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
|
||||
let e3 = e("eventually-rejected")
|
||||
let d3 = Promise<Int>.defer()
|
||||
let v3 = NSError(domain:PMKErrorDomain, code:Int(rand()), userInfo:nil)
|
||||
later {
|
||||
test(d3.promise, e3, v3)
|
||||
d3.reject(v3)
|
||||
}
|
||||
waitForExpectationsWithTimeout(1, handler: nil)
|
||||
}
|
||||
}
|
||||
@ -1,51 +0,0 @@
|
||||
import Accounts
|
||||
|
||||
extension ACAccountStore {
|
||||
public func renewCredentials(# account: ACAccount) -> Promise<ACAccountCredentialRenewResult> {
|
||||
return Promise { (fulfiller, rejecter) in
|
||||
self.renewCredentialsForAccount(account) {
|
||||
if $1 != nil {
|
||||
rejecter($1)
|
||||
} else {
|
||||
fulfiller($0)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public func requestAccessToAccounts(# type: ACAccountType, options:Dictionary<String, AnyObject>? = nil) -> Promise<Void> {
|
||||
return Promise { (fulfill, reject) in
|
||||
self.requestAccessToAccountsWithType(type, options:options) {
|
||||
if $1 != nil {
|
||||
reject($1)
|
||||
} else {
|
||||
fulfill()
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public func save(# account: ACAccount) -> Promise<Void> {
|
||||
return Promise { (fulfill, reject) in
|
||||
self.saveAccount(account) {
|
||||
if $0 {
|
||||
fulfill()
|
||||
} else {
|
||||
reject($1)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public func remove(# account: ACAccount) -> Promise<Void> {
|
||||
return Promise { (fulfill, reject) in
|
||||
self.removeAccount(account) {
|
||||
if $1 != nil {
|
||||
reject($1)
|
||||
} else {
|
||||
fulfill()
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -1,7 +0,0 @@
|
||||
import AVFoundation.AVAudioSession
|
||||
|
||||
extension AVAudioSession {
|
||||
func requestRecordPermission() -> Promise<Bool> {
|
||||
return Promise { (fulfill, _) in self.requestRecordPermission(fulfill) }
|
||||
}
|
||||
}
|
||||
@ -1,60 +0,0 @@
|
||||
import CloudKit
|
||||
|
||||
|
||||
extension CKContainer {
|
||||
public func accountStatus() -> Promise<CKAccountStatus> {
|
||||
return Promise { (fulfill, reject) in
|
||||
self.accountStatusWithCompletionHandler { (status, error) in
|
||||
if error == nil { fulfill(status) } else { reject(error) }
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public func requestApplicationPermission(applicationPermissions: CKApplicationPermissions) -> Promise<CKApplicationPermissionStatus> {
|
||||
return Promise { (fulfill, reject) in
|
||||
self.requestApplicationPermission(applicationPermissions) { (status, error) in
|
||||
if error == nil { fulfill(status) } else { reject(error) }
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public func statusForApplicationPermission(applicationPermissions: CKApplicationPermissions) -> Promise<CKApplicationPermissionStatus> {
|
||||
return Promise { (fulfill, reject) in
|
||||
self.statusForApplicationPermission(applicationPermissions) { (status, error) in
|
||||
if error == nil { fulfill(status) } else { reject(error) }
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public func discoverAllContactUserInfos() -> Promise<[CKDiscoveredUserInfo]> {
|
||||
return Promise { (fulfill, reject) in
|
||||
self.discoverAllContactUserInfosWithCompletionHandler { (userInfos, error) in
|
||||
if error == nil { fulfill(userInfos as! [CKDiscoveredUserInfo]) } else { reject(error) }
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public func discoverUserInfo(# email: String) -> Promise<CKDiscoveredUserInfo> {
|
||||
return Promise { (fulfill, reject) in
|
||||
self.discoverUserInfoWithEmailAddress(email) { (info, error) in
|
||||
if error == nil { fulfill(info) } else { reject(error) }
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public func discoverUserInfo(# recordID: CKRecordID) -> Promise<CKDiscoveredUserInfo> {
|
||||
return Promise { (fulfill, reject) in
|
||||
self.discoverUserInfoWithUserRecordID(recordID) { (info, error) in
|
||||
if error == nil { fulfill(info) } else { reject(error) }
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public func fetchUserRecordID() -> Promise<CKRecordID> {
|
||||
return Promise { (fulfill, reject) in
|
||||
self.fetchUserRecordIDWithCompletionHandler { (recordID, error) -> Void in
|
||||
if error == nil { fulfill(recordID) } else { reject(error) }
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -1,105 +0,0 @@
|
||||
import CloudKit.CKDatabase
|
||||
|
||||
private func proxy<T>(fulfill: (T)->(), reject: (NSError)->())(value: T!, error: NSError!) {
|
||||
if value != nil { fulfill(value!) } else { reject(error!) }
|
||||
}
|
||||
|
||||
extension CKDatabase {
|
||||
public func fetchRecordWithID(recordID: CKRecordID) -> Promise<CKRecord> {
|
||||
return Promise { f, r in
|
||||
self.fetchRecordWithID(recordID, completionHandler: proxy(f, r))
|
||||
}
|
||||
}
|
||||
|
||||
public func fetchRecordZoneWithID(recordZoneID: CKRecordZoneID) -> Promise<CKRecordZone> {
|
||||
return Promise { f, r in
|
||||
self.fetchRecordZoneWithID(recordZoneID, completionHandler: proxy(f, r))
|
||||
}
|
||||
}
|
||||
|
||||
public func fetchSubscriptionWithID(subscriptionID: String) -> Promise<CKSubscription> {
|
||||
return Promise { f, r in
|
||||
self.fetchSubscriptionWithID(subscriptionID, completionHandler: proxy(f, r))
|
||||
}
|
||||
}
|
||||
|
||||
public func fetchAllRecordZones() -> Promise<[CKRecordZone]> {
|
||||
return Promise { f, r in
|
||||
self.fetchAllRecordZonesWithCompletionHandler({
|
||||
proxy(f, r)(value: $0 as! [CKRecordZone], error: $1)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
public func fetchAllSubscriptions() -> Promise<[CKSubscription]> {
|
||||
return Promise { f, r in
|
||||
self.fetchAllSubscriptionsWithCompletionHandler({
|
||||
proxy(f, r)(value: $0 as! [CKSubscription], error: $1)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
public func save(record: CKRecord) -> Promise<CKRecord> {
|
||||
return Promise { f, r in
|
||||
self.saveRecord(record, completionHandler: proxy(f, r))
|
||||
}
|
||||
}
|
||||
|
||||
public func save(recordZone: CKRecordZone) -> Promise<CKRecordZone> {
|
||||
return Promise { f, r in
|
||||
self.saveRecordZone(recordZone, completionHandler: proxy(f, r))
|
||||
}
|
||||
}
|
||||
|
||||
public func save(subscription: CKSubscription) -> Promise<CKSubscription> {
|
||||
return Promise { f, r in
|
||||
self.saveSubscription(subscription, completionHandler: proxy(f, r))
|
||||
}
|
||||
}
|
||||
|
||||
public func deleteRecordWithID(recordID: CKRecordID) -> Promise<CKRecordID> {
|
||||
return Promise { f, r in
|
||||
self.deleteRecordWithID(recordID, completionHandler: proxy(f, r))
|
||||
}
|
||||
}
|
||||
|
||||
public func deleteRecordZoneWithID(zoneID: CKRecordZoneID) -> Promise<CKRecordZoneID> {
|
||||
return Promise { f, r in
|
||||
self.deleteRecordZoneWithID(zoneID, completionHandler: proxy(f, r))
|
||||
}
|
||||
}
|
||||
|
||||
public func deleteSubscriptionWithID(subscriptionID: String) -> Promise<String> {
|
||||
return Promise { f, r in
|
||||
self.deleteSubscriptionWithID(subscriptionID, completionHandler: proxy(f, r))
|
||||
}
|
||||
}
|
||||
|
||||
public func performQuery(query: CKQuery, inZoneWithID zoneID: CKRecordZoneID? = nil) -> Promise<[CKRecord]> {
|
||||
return Promise { f, r in
|
||||
self.performQuery(query, inZoneWithID: zoneID) {
|
||||
proxy(f, r)(value: $0 as! [CKRecord], error: $1)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public func performQuery(query: CKQuery, inZoneWithID zoneID: CKRecordZoneID? = nil) -> Promise<CKRecord?> {
|
||||
return Promise { fulfill, reject in
|
||||
self.performQuery(query, inZoneWithID: zoneID) { (records, error) in
|
||||
if records == nil {
|
||||
reject(error)
|
||||
} else if records.isEmpty {
|
||||
fulfill(nil)
|
||||
} else {
|
||||
fulfill((records as! [CKRecord])[0])
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public func fetchUserRecord(container: CKContainer = CKContainer.defaultContainer()) -> Promise<CKRecord> {
|
||||
return container.fetchUserRecordID().then { uid->Promise<CKRecord> in
|
||||
return self.fetchRecordWithID(uid)
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -1,40 +0,0 @@
|
||||
import CoreLocation.CLGeocoder
|
||||
|
||||
|
||||
extension CLGeocoder {
|
||||
public class func reverseGeocode(location: CLLocation) -> Promise<CLPlacemark> {
|
||||
return Promise { (fulfiller, rejecter) in
|
||||
CLGeocoder().reverseGeocodeLocation(location) {
|
||||
if $1 != nil {
|
||||
rejecter($1)
|
||||
} else {
|
||||
fulfiller($0[0] as! CLPlacemark)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public class func geocode(#addressDictionary: [String:String]) -> Promise<CLPlacemark> {
|
||||
return Promise { (fulfiller, rejecter) in
|
||||
CLGeocoder().geocodeAddressDictionary(addressDictionary) {
|
||||
if $1 != nil {
|
||||
rejecter($1)
|
||||
} else {
|
||||
fulfiller($0[0] as! CLPlacemark)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public class func geocode(#addressString: String) -> Promise<CLPlacemark> {
|
||||
return Promise { (fulfiller, rejecter) in
|
||||
CLGeocoder().geocodeAddressString(addressString) {
|
||||
if $1 != nil {
|
||||
rejecter($1)
|
||||
} else {
|
||||
fulfiller($0[0] as! CLPlacemark)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -1,139 +0,0 @@
|
||||
import CoreLocation.CLLocationManager
|
||||
|
||||
private class LocationManager: CLLocationManager, CLLocationManagerDelegate {
|
||||
let fulfiller: ([CLLocation]) -> Void
|
||||
let rejecter: (NSError) -> Void
|
||||
|
||||
@objc func locationManager(manager: CLLocationManager!, didUpdateLocations locations: [AnyObject]!) {
|
||||
fulfiller(locations as! [CLLocation])
|
||||
}
|
||||
|
||||
@objc func locationManager(manager: CLLocationManager!, didFailWithError error: NSError!) {
|
||||
rejecter(error)
|
||||
}
|
||||
|
||||
init(_ fulfiller: ([CLLocation]) -> Void, _ rejecter: (NSError) -> Void) {
|
||||
self.fulfiller = fulfiller
|
||||
self.rejecter = rejecter
|
||||
super.init()
|
||||
PMKRetain(self)
|
||||
delegate = self
|
||||
}
|
||||
}
|
||||
|
||||
private class AuthorizationCatcher: CLLocationManager, CLLocationManagerDelegate {
|
||||
let fulfill: (CLAuthorizationStatus) -> Void
|
||||
|
||||
init(fulfiller: (CLAuthorizationStatus)->(), auther: (CLLocationManager)->()) {
|
||||
fulfill = fulfiller
|
||||
super.init()
|
||||
let status = CLLocationManager.authorizationStatus()
|
||||
if status == .NotDetermined {
|
||||
delegate = self
|
||||
PMKRetain(self)
|
||||
auther(self)
|
||||
} else {
|
||||
fulfill(status)
|
||||
}
|
||||
}
|
||||
|
||||
@objc func locationManager(manager: CLLocationManager!, didChangeAuthorizationStatus status: CLAuthorizationStatus) {
|
||||
if status != .NotDetermined {
|
||||
fulfill(status)
|
||||
PMKRelease(self)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private func auther(requestAuthorizationType: CLLocationManager.RequestAuthorizationType)(manager: CLLocationManager)
|
||||
{
|
||||
func hasInfoPListKey(key: String) -> Bool {
|
||||
let value = NSBundle.mainBundle().objectForInfoDictionaryKey("NSLocationAlwaysUsageDescription") as? String ?? ""
|
||||
return !value.isEmpty
|
||||
}
|
||||
|
||||
#if os(iOS)
|
||||
switch requestAuthorizationType {
|
||||
case .Automatic:
|
||||
let always = hasInfoPListKey("NSLocationAlwaysUsageDescription")
|
||||
let whenInUse = hasInfoPListKey("NSLocationWhenInUseUsageDescription")
|
||||
if hasInfoPListKey("NSLocationAlwaysUsageDescription") {
|
||||
manager.requestAlwaysAuthorization()
|
||||
} else {
|
||||
manager.requestWhenInUseAuthorization()
|
||||
}
|
||||
case .WhenInUse:
|
||||
|
||||
manager.requestWhenInUseAuthorization()
|
||||
break
|
||||
case .Always:
|
||||
manager.requestAlwaysAuthorization()
|
||||
break
|
||||
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
extension CLLocationManager {
|
||||
|
||||
public enum RequestAuthorizationType {
|
||||
case Automatic
|
||||
case Always
|
||||
case WhenInUse
|
||||
}
|
||||
|
||||
/**
|
||||
Returns the most recent CLLocation.
|
||||
|
||||
@param requestAuthorizationType We read your Info plist and try to
|
||||
determine the authorization type we should request automatically. If you
|
||||
want to force one or the other, change this parameter from its default
|
||||
value.
|
||||
*/
|
||||
public class func promise(requestAuthorizationType: RequestAuthorizationType = .Automatic) -> Promise<CLLocation> {
|
||||
let p: Promise<[CLLocation]> = promise(requestAuthorizationType: requestAuthorizationType)
|
||||
return p.then { (locations)->CLLocation in
|
||||
return locations[locations.count - 1]
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
Returns the first batch of location objects a CLLocationManager instance
|
||||
provides.
|
||||
*/
|
||||
public class func promise(requestAuthorizationType: RequestAuthorizationType = .Automatic) -> Promise<[CLLocation]> {
|
||||
return promise(yield: auther(requestAuthorizationType))
|
||||
}
|
||||
|
||||
private class func promise(yield: (CLLocationManager)->() = { _ in }) -> Promise<[CLLocation]> {
|
||||
let deferred = Promise<[CLLocation]>.defer()
|
||||
let manager = LocationManager(deferred.fulfill, deferred.reject)
|
||||
yield(manager)
|
||||
manager.startUpdatingLocation()
|
||||
deferred.promise.finally {
|
||||
manager.delegate = nil
|
||||
manager.stopUpdatingLocation()
|
||||
PMKRelease(manager)
|
||||
}
|
||||
return deferred.promise
|
||||
}
|
||||
|
||||
/**
|
||||
Cannot error, despite the fact this might be more useful in some
|
||||
circumstances, we stick with our decision that errors are errors
|
||||
and errors only. Thus your catch handler is always catching failures
|
||||
and not being abused for logic.
|
||||
*/
|
||||
public class func requestAuthorization(type: RequestAuthorizationType = .Automatic) -> Promise<CLAuthorizationStatus> {
|
||||
let d = Promise<CLAuthorizationStatus>.defer()
|
||||
AuthorizationCatcher(fulfiller: d.fulfill, auther: auther(type))
|
||||
return d.promise
|
||||
}
|
||||
|
||||
@availability(*, deprecated=1.3.0)
|
||||
public class func requestAlwaysAuthorization() -> Promise<CLAuthorizationStatus> {
|
||||
return requestAuthorization(type: .Always)
|
||||
}
|
||||
}
|
||||
@ -1,28 +0,0 @@
|
||||
import MapKit
|
||||
|
||||
extension MKDirections {
|
||||
|
||||
public class func promise(request:MKDirectionsRequest) -> Promise<MKDirectionsResponse> {
|
||||
return Promise { (fulfiller, rejecter) in
|
||||
MKDirections(request:request).calculateDirectionsWithCompletionHandler {
|
||||
if $1 != nil {
|
||||
rejecter($1)
|
||||
} else {
|
||||
fulfiller($0)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public class func promise(request:MKDirectionsRequest) -> Promise<MKETAResponse> {
|
||||
return Promise { (fulfiller, rejecter) in
|
||||
MKDirections(request:request).calculateETAWithCompletionHandler {
|
||||
if $1 != nil {
|
||||
rejecter($1)
|
||||
} else {
|
||||
fulfiller($0)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -1,15 +0,0 @@
|
||||
import MapKit
|
||||
|
||||
extension MKMapSnapshotter {
|
||||
public func promise() -> Promise<MKMapSnapshot> {
|
||||
return Promise { (fulfiller, rejecter) in
|
||||
self.startWithCompletionHandler {
|
||||
if $1 != nil {
|
||||
rejecter($1)
|
||||
} else {
|
||||
fulfiller($0)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -1,36 +0,0 @@
|
||||
import Foundation.NSFileManager
|
||||
|
||||
|
||||
extension NSFileManager {
|
||||
func removeItemAtPath(path: String) -> Promise<String> {
|
||||
return dispatch_promise() {
|
||||
var error: NSError?
|
||||
self.removeItemAtPath(path, error:&error)
|
||||
return error ?? path
|
||||
}
|
||||
}
|
||||
|
||||
func copyItem(# from: String, to: String) -> Promise<String> {
|
||||
return dispatch_promise() {
|
||||
var error: NSError?
|
||||
self.copyItemAtPath(from, toPath:to, error:&error)
|
||||
return error ?? to
|
||||
}
|
||||
}
|
||||
|
||||
func moveItem(# from: String, to: String) -> Promise<String> {
|
||||
return dispatch_promise() {
|
||||
var error: NSError?
|
||||
self.moveItemAtPath(from, toPath: to, error: &error)
|
||||
return error ?? to
|
||||
}
|
||||
}
|
||||
|
||||
func createDirectoryAtPath(path: String, withIntermediateDirectories with: Bool = true, attributes: [NSObject: AnyObject]? = nil) -> Promise<String> {
|
||||
return dispatch_promise() {
|
||||
var error: NSError?
|
||||
self.createDirectoryAtPath(path, withIntermediateDirectories: with, attributes: attributes, error: &error)
|
||||
return error ?? path
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -1,33 +0,0 @@
|
||||
import Foundation
|
||||
|
||||
func NSJSONFromData(data: NSData) -> Promise<NSArray> {
|
||||
// work around ever-so-common Rails issue: https://github.com/rails/rails/issues/1742
|
||||
if data.isEqualToData(NSData(bytes: " ", length: 1)) {
|
||||
return Promise(value: NSArray()) // couldn’t do T() in generic function
|
||||
}
|
||||
return NSJSONFromDataT(data)
|
||||
}
|
||||
|
||||
func NSJSONFromData(data: NSData) -> Promise<NSDictionary> {
|
||||
if data.isEqualToData(NSData(bytes: " ", length: 1)) {
|
||||
return Promise(value: NSDictionary())
|
||||
}
|
||||
return NSJSONFromDataT(data)
|
||||
}
|
||||
|
||||
func NSJSONFromDataT<T>(data: NSData) -> Promise<T> {
|
||||
var error:NSError?
|
||||
let json:AnyObject? = NSJSONSerialization.JSONObjectWithData(data, options:nil, error:&error)
|
||||
|
||||
if error != nil {
|
||||
return Promise(error: error!)
|
||||
} else if let cast = json as? T {
|
||||
return Promise(value: cast)
|
||||
} else {
|
||||
var info: [NSObject: AnyObject] = [:]
|
||||
info[NSLocalizedDescriptionKey] = "The server returned JSON in an unexpected arrangement"
|
||||
if let jo:AnyObject = json { info[PMKJSONErrorJSONObjectKey] = jo }
|
||||
let error = NSError(domain:PMKErrorDomain, code:PMKJSONError, userInfo:info)
|
||||
return Promise(error: error)
|
||||
}
|
||||
}
|
||||
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user