fastlane 2.150.0.rc1 → 2.150.0.rc6
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/deliver/lib/deliver/download_screenshots.rb +48 -26
- data/deliver/lib/deliver/runner.rb +0 -17
- data/deliver/lib/deliver/submit_for_review.rb +79 -32
- data/deliver/lib/deliver/upload_metadata.rb +92 -21
- data/deliver/lib/deliver/upload_price_tier.rb +9 -2
- data/deliver/lib/deliver/upload_screenshots.rb +61 -9
- data/fastlane/lib/fastlane/actions/.hockey.rb.swp +0 -0
- data/fastlane/lib/fastlane/actions/.slack.rb.swp +0 -0
- data/fastlane/lib/fastlane/actions/.update_project_provisioning.rb.swp +0 -0
- data/fastlane/lib/fastlane/actions/docs/upload_to_app_store.md.erb +78 -85
- data/fastlane/lib/fastlane/actions/set_changelog.rb +23 -20
- data/fastlane/lib/fastlane/version.rb +1 -1
- data/fastlane/swift/FastlaneSwiftRunner/FastlaneSwiftRunner.xcodeproj/project.xcworkspace/xcuserdata/josh.xcuserdatad/UserInterfaceState.xcuserstate +0 -0
- data/fastlane_core/lib/fastlane_core/build_watcher.rb +4 -4
- data/fastlane_core/lib/fastlane_core/itunes_transporter.rb +89 -52
- data/pilot/lib/pilot/.manager.rb.swp +0 -0
- data/produce/lib/produce/itunes_connect.rb +43 -5
- data/spaceship/lib/spaceship/client.rb +4 -3
- data/spaceship/lib/spaceship/connect_api.rb +5 -1
- data/spaceship/lib/spaceship/{.DS_Store → connect_api/.DS_Store} +0 -0
- data/spaceship/lib/spaceship/connect_api/client.rb +50 -20
- data/spaceship/lib/spaceship/connect_api/file_uploader.rb +98 -0
- data/spaceship/lib/spaceship/connect_api/models/age_rating_declaration.rb +6 -2
- data/spaceship/lib/spaceship/connect_api/models/app.rb +35 -13
- data/spaceship/lib/spaceship/connect_api/models/app_info.rb +4 -11
- data/spaceship/lib/spaceship/connect_api/models/app_preview.rb +129 -0
- data/spaceship/lib/spaceship/connect_api/models/app_preview_set.rb +71 -0
- data/spaceship/lib/spaceship/connect_api/models/app_review_attachment.rb +18 -28
- data/spaceship/lib/spaceship/connect_api/models/app_screenshot.rb +88 -59
- data/spaceship/lib/spaceship/connect_api/models/app_screenshot_set.rb +26 -2
- data/spaceship/lib/spaceship/connect_api/models/app_store_version.rb +1 -0
- data/spaceship/lib/spaceship/connect_api/models/app_store_version_localization.rb +16 -0
- data/spaceship/lib/spaceship/connect_api/models/territory.rb +27 -0
- data/spaceship/lib/spaceship/connect_api/models/user.rb +2 -1
- data/spaceship/lib/spaceship/connect_api/tunes/tunes.rb +215 -74
- data/spaceship/lib/spaceship/connect_api/users/users.rb +13 -0
- metadata +16 -7
@@ -91,10 +91,14 @@ module Spaceship
|
|
91
91
|
|
92
92
|
def self.map_value_from_itc(key, value)
|
93
93
|
if ["gamblingAndContests", "unrestrictedWebAccess"].include?(key)
|
94
|
-
|
94
|
+
new_value = LEGACY_BOOLEAN_VALUE_ITC_MAP[value]
|
95
|
+
return value if new_value.nil?
|
96
|
+
return new_value
|
95
97
|
else
|
96
|
-
return LEGACY_RATING_VALUE_ITC_MAP[value]
|
98
|
+
return LEGACY_RATING_VALUE_ITC_MAP[value] || value
|
97
99
|
end
|
100
|
+
|
101
|
+
return value
|
98
102
|
end
|
99
103
|
|
100
104
|
#
|
@@ -54,16 +54,24 @@ module Spaceship
|
|
54
54
|
end
|
55
55
|
end
|
56
56
|
|
57
|
-
def self.create(name: nil, version_string: nil, sku: nil, primary_locale: nil, bundle_id: nil, platforms: nil)
|
58
|
-
Spaceship::ConnectAPI.post_app(
|
57
|
+
def self.create(name: nil, version_string: nil, sku: nil, primary_locale: nil, bundle_id: nil, platforms: nil, company_name: nil)
|
58
|
+
Spaceship::ConnectAPI.post_app(
|
59
|
+
name: name,
|
60
|
+
version_string: version_string,
|
61
|
+
sku: sku,
|
62
|
+
primary_locale: primary_locale,
|
63
|
+
bundle_id: bundle_id,
|
64
|
+
platforms: platforms,
|
65
|
+
company_name: company_name
|
66
|
+
)
|
59
67
|
end
|
60
68
|
|
61
69
|
def self.get(app_id: nil, includes: "appStoreVersions")
|
62
70
|
return Spaceship::ConnectAPI.get_app(app_id: app_id, includes: includes).first
|
63
71
|
end
|
64
72
|
|
65
|
-
def update(attributes: nil)
|
66
|
-
return Spaceship::ConnectAPI.patch_app(app_id: id, attributes: attributes)
|
73
|
+
def update(attributes: nil, app_price_tier_id: nil, territory_ids: nil)
|
74
|
+
return Spaceship::ConnectAPI.patch_app(app_id: id, attributes: attributes, app_price_tier_id: app_price_tier_id, territory_ids: territory_ids)
|
67
75
|
end
|
68
76
|
|
69
77
|
#
|
@@ -75,10 +83,13 @@ module Spaceship
|
|
75
83
|
Spaceship::ConnectAPI::AppInfo::AppStoreState::PREPARE_FOR_SUBMISSION,
|
76
84
|
Spaceship::ConnectAPI::AppInfo::AppStoreState::DEVELOPER_REJECTED,
|
77
85
|
Spaceship::ConnectAPI::AppInfo::AppStoreState::REJECTED,
|
78
|
-
Spaceship::ConnectAPI::AppInfo::AppStoreState::METADATA_REJECTED
|
86
|
+
Spaceship::ConnectAPI::AppInfo::AppStoreState::METADATA_REJECTED,
|
87
|
+
Spaceship::ConnectAPI::AppInfo::AppStoreState::WAITING_FOR_REVIEW,
|
88
|
+
Spaceship::ConnectAPI::AppInfo::AppStoreState::INVALID_BINARY
|
79
89
|
]
|
80
90
|
|
81
|
-
|
91
|
+
filter = { app: id }
|
92
|
+
resp = Spaceship::ConnectAPI.get_app_infos(filter: filter)
|
82
93
|
return resp.to_models.select do |model|
|
83
94
|
states.include?(model.app_store_state)
|
84
95
|
end.first
|
@@ -95,11 +106,6 @@ module Spaceship
|
|
95
106
|
return resp.to_models
|
96
107
|
end
|
97
108
|
|
98
|
-
def update_app_price_tier(app_price_tier_id: nil)
|
99
|
-
resp = Spaceship::ConnectAPI.patch_app_app_prices(app_id: id, app_price_tier_id: app_price_tier_id)
|
100
|
-
return resp.first
|
101
|
-
end
|
102
|
-
|
103
109
|
#
|
104
110
|
# App Store Versions
|
105
111
|
#
|
@@ -142,11 +148,17 @@ module Spaceship
|
|
142
148
|
Spaceship::ConnectAPI::AppStoreVersion::AppStoreState::PREPARE_FOR_SUBMISSION,
|
143
149
|
Spaceship::ConnectAPI::AppStoreVersion::AppStoreState::DEVELOPER_REJECTED,
|
144
150
|
Spaceship::ConnectAPI::AppStoreVersion::AppStoreState::REJECTED,
|
145
|
-
Spaceship::ConnectAPI::AppStoreVersion::AppStoreState::METADATA_REJECTED
|
151
|
+
Spaceship::ConnectAPI::AppStoreVersion::AppStoreState::METADATA_REJECTED,
|
152
|
+
Spaceship::ConnectAPI::AppStoreVersion::AppStoreState::WAITING_FOR_REVIEW,
|
153
|
+
Spaceship::ConnectAPI::AppStoreVersion::AppStoreState::INVALID_BINARY
|
146
154
|
].join(","),
|
147
155
|
platform: platform
|
148
156
|
}
|
149
|
-
|
157
|
+
|
158
|
+
# Get the latest version
|
159
|
+
return get_app_store_versions(filter: filter, includes: includes)
|
160
|
+
.sort_by { |v| Gem::Version.new(v.version_string) }
|
161
|
+
.last
|
150
162
|
end
|
151
163
|
|
152
164
|
def get_app_store_versions(filter: {}, includes: nil, limit: nil, sort: nil)
|
@@ -224,6 +236,16 @@ module Spaceship
|
|
224
236
|
).all_pages
|
225
237
|
return resps.flat_map(&:to_models).first
|
226
238
|
end
|
239
|
+
|
240
|
+
#
|
241
|
+
# Users
|
242
|
+
#
|
243
|
+
|
244
|
+
def add_users(user_ids: nil)
|
245
|
+
user_ids.each do |user_id|
|
246
|
+
Spaceship::ConnectAPI.add_user_visible_apps(user_id: user_id, app_ids: [id])
|
247
|
+
end
|
248
|
+
end
|
227
249
|
end
|
228
250
|
end
|
229
251
|
end
|
@@ -16,6 +16,7 @@ module Spaceship
|
|
16
16
|
REJECTED = "REJECTED"
|
17
17
|
PREPARE_FOR_SUBMISSION = "PREPARE_FOR_SUBMISSION"
|
18
18
|
METADATA_REJECTED = "METADATA_REJECTED"
|
19
|
+
INVALID_BINARY = "INVALID_BINARY"
|
19
20
|
end
|
20
21
|
|
21
22
|
module AppStoreAgeRating
|
@@ -38,19 +39,11 @@ module Spaceship
|
|
38
39
|
#
|
39
40
|
|
40
41
|
def update(filter: {}, includes: nil, limit: nil, sort: nil)
|
41
|
-
Spaceship::ConnectAPI.patch_app_info(app_info_id: id)
|
42
|
+
Spaceship::ConnectAPI.patch_app_info(app_info_id: id).first
|
42
43
|
end
|
43
44
|
|
44
|
-
def update_categories(
|
45
|
-
Spaceship::ConnectAPI.patch_app_info_categories(
|
46
|
-
app_info_id: id,
|
47
|
-
primary_category_id: primary_category_id,
|
48
|
-
secondary_category_id: secondary_category_id,
|
49
|
-
primary_subcategory_one_id: primary_subcategory_one_id,
|
50
|
-
primary_subcategory_two_id: primary_subcategory_two_id,
|
51
|
-
secondary_subcategory_one_id: secondary_subcategory_one_id,
|
52
|
-
secondary_subcategory_two_id: secondary_subcategory_two_id
|
53
|
-
)
|
45
|
+
def update_categories(category_id_map: nil)
|
46
|
+
Spaceship::ConnectAPI.patch_app_info_categories(app_info_id: id, category_id_map: category_id_map).first
|
54
47
|
end
|
55
48
|
|
56
49
|
def delete!(filter: {}, includes: nil, limit: nil, sort: nil)
|
@@ -0,0 +1,129 @@
|
|
1
|
+
require_relative '../model'
|
2
|
+
require_relative '../file_uploader'
|
3
|
+
require 'spaceship/globals'
|
4
|
+
|
5
|
+
require 'digest/md5'
|
6
|
+
|
7
|
+
module Spaceship
|
8
|
+
class ConnectAPI
|
9
|
+
class AppPreview
|
10
|
+
include Spaceship::ConnectAPI::Model
|
11
|
+
|
12
|
+
attr_accessor :file_size
|
13
|
+
attr_accessor :file_name
|
14
|
+
attr_accessor :source_file_checksum
|
15
|
+
attr_accessor :preview_frame_time_code
|
16
|
+
attr_accessor :mime_type
|
17
|
+
attr_accessor :video_url
|
18
|
+
attr_accessor :preview_image
|
19
|
+
attr_accessor :upload_operations
|
20
|
+
attr_accessor :asset_deliver_state
|
21
|
+
attr_accessor :upload
|
22
|
+
|
23
|
+
attr_mapping({
|
24
|
+
"fileSize" => "file_size",
|
25
|
+
"fileName" => "file_name",
|
26
|
+
"sourceFileChecksum" => "source_file_checksum",
|
27
|
+
"previewFrameTimeCode" => "preview_frame_time_code",
|
28
|
+
"mimeType" => "mime_type",
|
29
|
+
"videoUrl" => "video_url",
|
30
|
+
"previewImage" => "preview_image",
|
31
|
+
"uploadOperations" => "upload_operations",
|
32
|
+
"assetDeliveryState" => "asset_delivery_state",
|
33
|
+
"uploaded" => "uploaded"
|
34
|
+
})
|
35
|
+
|
36
|
+
def self.type
|
37
|
+
return "appPreviews"
|
38
|
+
end
|
39
|
+
|
40
|
+
def complete?
|
41
|
+
(asset_delivery_state || {})["state"] == "COMPLETE"
|
42
|
+
end
|
43
|
+
|
44
|
+
#
|
45
|
+
# API
|
46
|
+
#
|
47
|
+
|
48
|
+
def self.get(app_preview_id: nil)
|
49
|
+
Spaceship::ConnectAPI.get_app_preview(app_preview_id: app_preview_id).first
|
50
|
+
end
|
51
|
+
|
52
|
+
# Creates an AppPreview in an AppPreviewSet
|
53
|
+
# Setting the optional frame_time_code will force polling until video is done processing
|
54
|
+
# @param app_preview_set_id The AppPreviewSet id
|
55
|
+
# @param path The path of the file
|
56
|
+
# @param frame_time_code The time code for the preview still frame (ex: "00:00:07:01")
|
57
|
+
def self.create(app_preview_set_id: nil, path: nil, frame_time_code: nil)
|
58
|
+
require 'faraday'
|
59
|
+
|
60
|
+
filename = File.basename(path)
|
61
|
+
filesize = File.size(path)
|
62
|
+
bytes = File.binread(path)
|
63
|
+
|
64
|
+
post_attributes = {
|
65
|
+
fileSize: filesize,
|
66
|
+
fileName: filename
|
67
|
+
}
|
68
|
+
|
69
|
+
# Create placeholder
|
70
|
+
preview = Spaceship::ConnectAPI.post_app_preview(
|
71
|
+
app_preview_set_id: app_preview_set_id,
|
72
|
+
attributes: post_attributes
|
73
|
+
).to_models.first
|
74
|
+
|
75
|
+
# Upload the file
|
76
|
+
upload_operations = preview.upload_operations
|
77
|
+
Spaceship::ConnectAPI::FileUploader.upload(upload_operations, bytes)
|
78
|
+
|
79
|
+
# Update file uploading complete
|
80
|
+
patch_attributes = {
|
81
|
+
uploaded: true,
|
82
|
+
sourceFileChecksum: Digest::MD5.hexdigest(bytes)
|
83
|
+
}
|
84
|
+
|
85
|
+
begin
|
86
|
+
preview = Spaceship::ConnectAPI.patch_app_preview(
|
87
|
+
app_preview_id: preview.id,
|
88
|
+
attributes: patch_attributes
|
89
|
+
).to_models.first
|
90
|
+
rescue => error
|
91
|
+
puts("Failed to patch app preview. Update may have gone through so verifying") if Spaceship::Globals.verbose?
|
92
|
+
|
93
|
+
preview = Spaceship::ConnectAPI::AppPreview.get(app_preview_id: preview.id)
|
94
|
+
raise error unless preview.complete?
|
95
|
+
end
|
96
|
+
|
97
|
+
# Poll for video processing completion to set still frame time
|
98
|
+
unless frame_time_code.nil?
|
99
|
+
loop do
|
100
|
+
unless preview.video_url.nil?
|
101
|
+
puts("Preview processing complete!") if Spaceship::Globals.verbose?
|
102
|
+
preview = preview.update(attributes: {
|
103
|
+
previewFrameTimeCode: frame_time_code
|
104
|
+
})
|
105
|
+
puts("Updated preview frame time code!") if Spaceship::Globals.verbose?
|
106
|
+
break
|
107
|
+
end
|
108
|
+
|
109
|
+
sleep_time = 30
|
110
|
+
puts("Waiting #{sleep_time} seconds before checking status of processing...") if Spaceship::Globals.verbose?
|
111
|
+
sleep(sleep_time)
|
112
|
+
|
113
|
+
preview = Spaceship::ConnectAPI::AppPreview.get(app_preview_id: preview.id)
|
114
|
+
end
|
115
|
+
end
|
116
|
+
|
117
|
+
preview
|
118
|
+
end
|
119
|
+
|
120
|
+
def update(attributes: nil)
|
121
|
+
Spaceship::ConnectAPI.patch_app_preview(app_preview_id: id, attributes: attributes)
|
122
|
+
end
|
123
|
+
|
124
|
+
def delete!(filter: {}, includes: nil, limit: nil, sort: nil)
|
125
|
+
Spaceship::ConnectAPI.delete_app_preview(app_preview_id: id)
|
126
|
+
end
|
127
|
+
end
|
128
|
+
end
|
129
|
+
end
|
@@ -0,0 +1,71 @@
|
|
1
|
+
require_relative '../model'
|
2
|
+
require_relative './app_preview'
|
3
|
+
|
4
|
+
module Spaceship
|
5
|
+
class ConnectAPI
|
6
|
+
class AppPreviewSet
|
7
|
+
include Spaceship::ConnectAPI::Model
|
8
|
+
|
9
|
+
attr_accessor :preview_type
|
10
|
+
|
11
|
+
attr_accessor :app_previews
|
12
|
+
|
13
|
+
module PreviewType
|
14
|
+
IPHONE_35 = "IPHONE_35"
|
15
|
+
IPHONE_40 = "IPHONE_40"
|
16
|
+
IPHONE_47 = "IPHONE_47"
|
17
|
+
IPHONE_55 = "IPHONE_55"
|
18
|
+
IPHONE_58 = "IPHONE_58"
|
19
|
+
IPHONE_65 = "IPHONE_65"
|
20
|
+
|
21
|
+
IPAD_97 = "IPAD_97"
|
22
|
+
IPAD_105 = "IPAD_105"
|
23
|
+
IPAD_PRO_3GEN_11 = "IPAD_PRO_3GEN_11"
|
24
|
+
IPAD_PRO_129 = "IPAD_PRO_129"
|
25
|
+
IPAD_PRO_3GEN_129 = "IPAD_PRO_3GEN_129"
|
26
|
+
|
27
|
+
DESKTOP = "DESKTOP"
|
28
|
+
|
29
|
+
ALL = [
|
30
|
+
IPHONE_35,
|
31
|
+
IPHONE_40,
|
32
|
+
IPHONE_47,
|
33
|
+
IPHONE_55,
|
34
|
+
IPHONE_58,
|
35
|
+
IPHONE_65,
|
36
|
+
|
37
|
+
IPAD_97,
|
38
|
+
IPAD_105,
|
39
|
+
IPAD_PRO_3GEN_11,
|
40
|
+
IPAD_PRO_129,
|
41
|
+
IPAD_PRO_3GEN_129,
|
42
|
+
|
43
|
+
DESKTOP
|
44
|
+
]
|
45
|
+
end
|
46
|
+
|
47
|
+
attr_mapping({
|
48
|
+
"previewType" => "preview_type",
|
49
|
+
|
50
|
+
"appPreviews" => "app_previews"
|
51
|
+
})
|
52
|
+
|
53
|
+
def self.type
|
54
|
+
return "appPreviewSets"
|
55
|
+
end
|
56
|
+
|
57
|
+
#
|
58
|
+
# API
|
59
|
+
#
|
60
|
+
|
61
|
+
def self.all(filter: {}, includes: nil, limit: nil, sort: nil)
|
62
|
+
resp = Spaceship::ConnectAPI.get_app_preview_sets(filter: filter, includes: includes, limit: limit, sort: sort)
|
63
|
+
return resp.to_models
|
64
|
+
end
|
65
|
+
|
66
|
+
def upload_preview(path: nil, frame_time_code: nil)
|
67
|
+
return Spaceship::ConnectAPI::AppPreview.create(app_preview_set_id: id, path: path, frame_time_code: frame_time_code)
|
68
|
+
end
|
69
|
+
end
|
70
|
+
end
|
71
|
+
end
|
@@ -1,4 +1,7 @@
|
|
1
1
|
require_relative '../model'
|
2
|
+
require_relative '../file_uploader'
|
3
|
+
require 'digest/md5'
|
4
|
+
|
2
5
|
module Spaceship
|
3
6
|
class ConnectAPI
|
4
7
|
class AppReviewAttachment
|
@@ -31,46 +34,33 @@ module Spaceship
|
|
31
34
|
|
32
35
|
filename = File.basename(path)
|
33
36
|
filesize = File.size(path)
|
34
|
-
|
37
|
+
bytes = File.binread(path)
|
35
38
|
|
36
39
|
post_attributes = {
|
37
40
|
fileSize: filesize,
|
38
41
|
fileName: filename
|
39
42
|
}
|
40
43
|
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
# "length": 57365,
|
47
|
-
# "offset": 0,
|
48
|
-
# "requestHeaders": [
|
49
|
-
# {
|
50
|
-
# "name": "Content-Type",
|
51
|
-
# "value": "image/png"
|
52
|
-
# }
|
53
|
-
# ]
|
54
|
-
# }
|
55
|
-
upload_operation = post_resp.upload_operations.first
|
56
|
-
|
57
|
-
headers = {}
|
58
|
-
upload_operation["requestHeaders"].each do |hash|
|
59
|
-
headers[hash["name"]] = hash["value"]
|
60
|
-
end
|
44
|
+
# Create placeholder
|
45
|
+
attachment = Spaceship::ConnectAPI.post_app_review_attachment(
|
46
|
+
app_store_review_detail_id: app_store_review_detail_id,
|
47
|
+
attributes: post_attributes
|
48
|
+
).to_models.first
|
61
49
|
|
62
|
-
|
63
|
-
|
64
|
-
|
65
|
-
headers
|
66
|
-
)
|
50
|
+
# Upload the file
|
51
|
+
upload_operations = attachment.upload_operations
|
52
|
+
Spaceship::ConnectAPI::FileUploader.upload(upload_operations, bytes)
|
67
53
|
|
54
|
+
# Update file uploading complete
|
68
55
|
patch_attributes = {
|
69
56
|
uploaded: true,
|
70
|
-
sourceFileChecksum:
|
57
|
+
sourceFileChecksum: Digest::MD5.hexdigest(bytes)
|
71
58
|
}
|
72
59
|
|
73
|
-
Spaceship::ConnectAPI.patch_app_review_attachment(
|
60
|
+
Spaceship::ConnectAPI.patch_app_review_attachment(
|
61
|
+
app_review_attachment_id: attachment.id,
|
62
|
+
attributes: patch_attributes
|
63
|
+
).to_models.first
|
74
64
|
end
|
75
65
|
|
76
66
|
def delete!(filter: {}, includes: nil, limit: nil, sort: nil)
|
@@ -1,4 +1,9 @@
|
|
1
1
|
require_relative '../model'
|
2
|
+
require_relative '../file_uploader'
|
3
|
+
require 'spaceship/globals'
|
4
|
+
|
5
|
+
require 'digest/md5'
|
6
|
+
|
2
7
|
module Spaceship
|
3
8
|
class ConnectAPI
|
4
9
|
class AppScreenshot
|
@@ -13,36 +18,6 @@ module Spaceship
|
|
13
18
|
attr_accessor :asset_delivery_state
|
14
19
|
attr_accessor :uploaded
|
15
20
|
|
16
|
-
# "fileSize": 92542,
|
17
|
-
# "fileName": "ftl_3241d62418767c0aa9b889b020c4f8db_45455763d4aaf7b18ee0045bc787f3de.png",
|
18
|
-
# "sourceFileChecksum": "c237fd7852ed8f9285d16d9a28d2ec25",
|
19
|
-
# "imageAsset": {
|
20
|
-
# "templateUrl": "https://is4-ssl.mzstatic.com/image/thumb/Purple113/v4/61/18/68/61186886-b234-5bd0-1f4a-563124f18511/pr_source.png/{w}x{h}bb.{f}",
|
21
|
-
# "width": 2048,
|
22
|
-
# "height": 2732
|
23
|
-
# },
|
24
|
-
# "assetToken": "Purple113/v4/61/18/68/61186886-b234-5bd0-1f4a-563124f18511/pr_source.png",
|
25
|
-
# "assetType": "SortedJ99ScreenShot",
|
26
|
-
# "uploadOperations": null,
|
27
|
-
# "assetDeliveryState": {
|
28
|
-
# "errors": [],
|
29
|
-
# "warnings": null,
|
30
|
-
# "state": "COMPLETE"
|
31
|
-
# },
|
32
|
-
# "uploaded": null
|
33
|
-
|
34
|
-
# "assetDeliveryState": {
|
35
|
-
# "errors": [],
|
36
|
-
# "warnings": null,
|
37
|
-
# "state": "AWAITING_UPLOAD"
|
38
|
-
# },
|
39
|
-
|
40
|
-
# "assetDeliveryState": {
|
41
|
-
# "errors": [],
|
42
|
-
# "warnings": null,
|
43
|
-
# "state": "UPLOAD_COMPLETE"
|
44
|
-
# },
|
45
|
-
|
46
21
|
attr_mapping({
|
47
22
|
"fileName" => "file_name",
|
48
23
|
"sourceFileChecksum" => "source_file_checksum",
|
@@ -58,55 +33,109 @@ module Spaceship
|
|
58
33
|
return "appScreenshots"
|
59
34
|
end
|
60
35
|
|
36
|
+
def complete?
|
37
|
+
(asset_delivery_state || {})["state"] == "COMPLETE"
|
38
|
+
end
|
39
|
+
|
40
|
+
def error?
|
41
|
+
(asset_delivery_state || {})["state"] == "FAILED"
|
42
|
+
end
|
43
|
+
|
44
|
+
def error_messages
|
45
|
+
errors = (asset_delivery_state || {})["errors"]
|
46
|
+
(errors || []).map do |error|
|
47
|
+
[error["code"], error["description"]].compact.join(" - ")
|
48
|
+
end
|
49
|
+
end
|
50
|
+
|
51
|
+
# This does not download the source image (exact image that was uploaded)
|
52
|
+
# This downloads a modified version.
|
53
|
+
# This image won't have the same checksums as source_file_checksum.
|
54
|
+
#
|
55
|
+
# There is an open radar for allowing downloading of source file.
|
56
|
+
# https://openradar.appspot.com/radar?id=4980344105205760
|
57
|
+
def image_asset_url(width: nil, height: nil, type: "png")
|
58
|
+
return nil if image_asset.nil?
|
59
|
+
|
60
|
+
template_url = image_asset["templateUrl"]
|
61
|
+
width ||= image_asset["width"]
|
62
|
+
height ||= image_asset["height"]
|
63
|
+
|
64
|
+
return template_url
|
65
|
+
.gsub("{w}", width.to_s)
|
66
|
+
.gsub("{h}", height.to_s)
|
67
|
+
.gsub("{f}", type)
|
68
|
+
end
|
69
|
+
|
61
70
|
#
|
62
71
|
# API
|
63
72
|
#
|
73
|
+
#
|
64
74
|
|
65
|
-
def self.create(app_screenshot_set_id: nil, path: nil)
|
75
|
+
def self.create(app_screenshot_set_id: nil, path: nil, wait_for_processing: true)
|
66
76
|
require 'faraday'
|
67
77
|
|
68
78
|
filename = File.basename(path)
|
69
79
|
filesize = File.size(path)
|
70
|
-
|
80
|
+
bytes = File.binread(path)
|
71
81
|
|
72
82
|
post_attributes = {
|
73
83
|
fileSize: filesize,
|
74
84
|
fileName: filename
|
75
85
|
}
|
76
86
|
|
77
|
-
|
78
|
-
|
79
|
-
|
80
|
-
|
81
|
-
|
82
|
-
# "length": 57365,
|
83
|
-
# "offset": 0,
|
84
|
-
# "requestHeaders": [
|
85
|
-
# {
|
86
|
-
# "name": "Content-Type",
|
87
|
-
# "value": "image/png"
|
88
|
-
# }
|
89
|
-
# ]
|
90
|
-
# }
|
91
|
-
upload_operation = post_resp.upload_operations.first
|
92
|
-
|
93
|
-
headers = {}
|
94
|
-
upload_operation["requestHeaders"].each do |hash|
|
95
|
-
headers[hash["name"]] = hash["value"]
|
96
|
-
end
|
87
|
+
# Create placeholder
|
88
|
+
screenshot = Spaceship::ConnectAPI.post_app_screenshot(
|
89
|
+
app_screenshot_set_id: app_screenshot_set_id,
|
90
|
+
attributes: post_attributes
|
91
|
+
).first
|
97
92
|
|
98
|
-
|
99
|
-
|
100
|
-
|
101
|
-
headers
|
102
|
-
)
|
93
|
+
# Upload the file
|
94
|
+
upload_operations = screenshot.upload_operations
|
95
|
+
Spaceship::ConnectAPI::FileUploader.upload(upload_operations, bytes)
|
103
96
|
|
97
|
+
# Update file uploading complete
|
104
98
|
patch_attributes = {
|
105
99
|
uploaded: true,
|
106
|
-
sourceFileChecksum:
|
100
|
+
sourceFileChecksum: Digest::MD5.hexdigest(bytes)
|
107
101
|
}
|
108
102
|
|
109
|
-
|
103
|
+
# Patch screenshot that file upload is complete
|
104
|
+
# Catch error if patch retries due to 504. Origal patch
|
105
|
+
# may go through by return response as 504.
|
106
|
+
begin
|
107
|
+
screenshot = Spaceship::ConnectAPI.patch_app_screenshot(
|
108
|
+
app_screenshot_id: screenshot.id,
|
109
|
+
attributes: patch_attributes
|
110
|
+
).first
|
111
|
+
rescue => error
|
112
|
+
puts("Failed to patch app screenshot. Update may have gone through so verifying") if Spaceship::Globals.verbose?
|
113
|
+
|
114
|
+
screenshot = Spaceship::ConnectAPI.get_app_screenshot(app_screenshot_id: screenshot.id).first
|
115
|
+
raise error unless screenshot.complete?
|
116
|
+
end
|
117
|
+
|
118
|
+
# Wait for processing
|
119
|
+
if wait_for_processing
|
120
|
+
loop do
|
121
|
+
if screenshot.complete?
|
122
|
+
puts("Screenshot processing complete!") if Spaceship::Globals.verbose?
|
123
|
+
break
|
124
|
+
elsif screenshot.error?
|
125
|
+
messages = ["Error processing screenshot '#{screenshot.file_name}'"] + screenshot.error_messages
|
126
|
+
raise messages.join(". ")
|
127
|
+
end
|
128
|
+
|
129
|
+
# Poll every 2 seconds
|
130
|
+
sleep_time = 2
|
131
|
+
puts("Waiting #{sleep_time} seconds before checking status of processing...") if Spaceship::Globals.verbose?
|
132
|
+
sleep(sleep_time)
|
133
|
+
|
134
|
+
screenshot = Spaceship::ConnectAPI.get_app_screenshot(app_screenshot_id: screenshot.id).first
|
135
|
+
end
|
136
|
+
end
|
137
|
+
|
138
|
+
return screenshot
|
110
139
|
end
|
111
140
|
|
112
141
|
def delete!(filter: {}, includes: nil, limit: nil, sort: nil)
|