fastlane 2.157.0 → 2.158.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (52) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +72 -72
  3. data/deliver/lib/deliver/app_screenshot_iterator.rb +1 -1
  4. data/deliver/lib/deliver/runner.rb +5 -3
  5. data/fastlane/lib/fastlane/actions/.hockey.rb.swp +0 -0
  6. data/fastlane/lib/fastlane/actions/{.git_commit.rb.swp → .slack.rb.swp} +0 -0
  7. data/fastlane/lib/fastlane/actions/.update_project_provisioning.rb.swp +0 -0
  8. data/fastlane/lib/fastlane/actions/app_store_build_number.rb +12 -8
  9. data/fastlane/lib/fastlane/actions/download_dsyms.rb +89 -68
  10. data/fastlane/lib/fastlane/actions/set_changelog.rb +3 -2
  11. data/fastlane/lib/fastlane/version.rb +1 -1
  12. data/fastlane/swift/Deliverfile.swift +1 -1
  13. data/fastlane/swift/DeliverfileProtocol.swift +1 -1
  14. data/fastlane/swift/Fastlane.swift +18 -12
  15. data/fastlane/swift/FastlaneSwiftRunner/FastlaneSwiftRunner.xcodeproj/project.xcworkspace/xcuserdata/josh.xcuserdatad/UserInterfaceState.xcuserstate +0 -0
  16. data/fastlane/swift/Gymfile.swift +1 -1
  17. data/fastlane/swift/GymfileProtocol.swift +1 -1
  18. data/fastlane/swift/Matchfile.swift +1 -1
  19. data/fastlane/swift/MatchfileProtocol.swift +1 -1
  20. data/fastlane/swift/Precheckfile.swift +1 -1
  21. data/fastlane/swift/PrecheckfileProtocol.swift +5 -1
  22. data/fastlane/swift/Scanfile.swift +1 -1
  23. data/fastlane/swift/ScanfileProtocol.swift +1 -1
  24. data/fastlane/swift/Screengrabfile.swift +1 -1
  25. data/fastlane/swift/ScreengrabfileProtocol.swift +1 -1
  26. data/fastlane/swift/Snapshotfile.swift +1 -1
  27. data/fastlane/swift/SnapshotfileProtocol.swift +1 -1
  28. data/fastlane_core/lib/fastlane_core/command_executor.rb +1 -0
  29. data/match/lib/match/spaceship_ensure.rb +5 -5
  30. data/{fastlane/lib/fastlane/.erb_template_helper.rb.swp → pilot/lib/pilot/.manager.rb.swp} +0 -0
  31. data/pilot/lib/pilot/build_manager.rb +0 -3
  32. data/pilot/lib/pilot/manager.rb +1 -1
  33. data/precheck/lib/precheck/options.rb +9 -0
  34. data/precheck/lib/precheck/rule_processor.rb +94 -60
  35. data/precheck/lib/precheck/runner.rb +6 -4
  36. data/produce/lib/produce/itunes_connect.rb +3 -2
  37. data/screengrab/lib/screengrab/runner.rb +28 -10
  38. data/sigh/lib/assets/resign.sh +9 -6
  39. data/sigh/lib/sigh/runner.rb +3 -2
  40. data/spaceship/lib/spaceship/client.rb +1 -0
  41. data/spaceship/lib/spaceship/connect_api.rb +1 -0
  42. data/spaceship/lib/spaceship/{.DS_Store → connect_api/.DS_Store} +0 -0
  43. data/spaceship/lib/spaceship/connect_api/client.rb +32 -13
  44. data/spaceship/lib/spaceship/connect_api/file_uploader.rb +2 -0
  45. data/spaceship/lib/spaceship/connect_api/models/app.rb +5 -5
  46. data/spaceship/lib/spaceship/connect_api/models/app_price_point.rb +26 -0
  47. data/spaceship/lib/spaceship/connect_api/models/app_store_version.rb +7 -1
  48. data/spaceship/lib/spaceship/connect_api/models/app_store_version_phased_release.rb +21 -0
  49. data/spaceship/lib/spaceship/connect_api/spaceship.rb +10 -6
  50. data/spaceship/lib/spaceship/connect_api/testflight/testflight.rb +50 -50
  51. data/spaceship/lib/spaceship/connect_api/tunes/tunes.rb +20 -0
  52. metadata +25 -21
@@ -4,9 +4,10 @@ module Fastlane
4
4
  def self.run(params)
5
5
  require 'spaceship'
6
6
 
7
+ # Team selection passed though FASTLANE_ITC_TEAM_ID and FASTLANE_ITC_TEAM_NAME environment variables
8
+ # Prompts select team if multiple teams and none specified
7
9
  UI.message("Login to App Store Connect (#{params[:username]})")
8
- Spaceship::ConnectAPI.login(params[:username])
9
- Spaceship::ConnectAPI.select_team
10
+ Spaceship::ConnectAPI.login(params[:username], use_portal: false, use_tunes: true)
10
11
  UI.message("Login successful")
11
12
 
12
13
  app = Spaceship::ConnectAPI::App.find(params[:app_identifier])
@@ -1,5 +1,5 @@
1
1
  module Fastlane
2
- VERSION = '2.157.0'.freeze
2
+ VERSION = '2.158.0'.freeze
3
3
  DESCRIPTION = "The easiest way to automate beta deployments and releases for your iOS and Android apps".freeze
4
4
  MINIMUM_XCODE_RELEASE = "7.0".freeze
5
5
  RUBOCOP_REQUIREMENT = '0.49.1'.freeze
@@ -14,4 +14,4 @@ class Deliverfile: DeliverfileProtocol {
14
14
  // during the `init` process, and you won't see this message
15
15
  }
16
16
 
17
- // Generated with fastlane 2.157.0
17
+ // Generated with fastlane 2.158.0
@@ -245,4 +245,4 @@ extension DeliverfileProtocol {
245
245
 
246
246
  // Please don't remove the lines below
247
247
  // They are used to detect outdated files
248
- // FastlaneRunnerAPIVersion [0.9.35]
248
+ // FastlaneRunnerAPIVersion [0.9.40]
@@ -1952,6 +1952,7 @@ func chatwork(apiToken: String,
1952
1952
  - username: Your Apple ID Username
1953
1953
  - teamId: The ID of your App Store Connect team if you're in multiple teams
1954
1954
  - teamName: The name of your App Store Connect team if you're in multiple teams
1955
+ - platform: The platform to use (optional)
1955
1956
  - defaultRuleLevel: The default rule level unless otherwise configured
1956
1957
  - includeInAppPurchases: Should check in-app purchases?
1957
1958
  - negativeAppleSentiment: mentioning  in a way that could be considered negative
@@ -1973,6 +1974,7 @@ func checkAppStoreMetadata(appIdentifier: String,
1973
1974
  username: String,
1974
1975
  teamId: String? = nil,
1975
1976
  teamName: String? = nil,
1977
+ platform: String = "ios",
1976
1978
  defaultRuleLevel: Any = "error",
1977
1979
  includeInAppPurchases: Bool = true,
1978
1980
  negativeAppleSentiment: Any? = nil,
@@ -1990,6 +1992,7 @@ func checkAppStoreMetadata(appIdentifier: String,
1990
1992
  RubyCommand.Argument(name: "username", value: username),
1991
1993
  RubyCommand.Argument(name: "team_id", value: teamId),
1992
1994
  RubyCommand.Argument(name: "team_name", value: teamName),
1995
+ RubyCommand.Argument(name: "platform", value: platform),
1993
1996
  RubyCommand.Argument(name: "default_rule_level", value: defaultRuleLevel),
1994
1997
  RubyCommand.Argument(name: "include_in_app_purchases", value: includeInAppPurchases),
1995
1998
  RubyCommand.Argument(name: "negative_apple_sentiment", value: negativeAppleSentiment),
@@ -2886,7 +2889,7 @@ func downloadDsyms(username: String,
2886
2889
  func downloadFromPlayStore(packageName: String,
2887
2890
  versionName: String? = nil,
2888
2891
  track: String = "production",
2889
- metadataPath: String? = nil,
2892
+ metadataPath: String = "./metadata",
2890
2893
  key: String? = nil,
2891
2894
  issuer: String? = nil,
2892
2895
  jsonKey: String? = nil,
@@ -5470,6 +5473,7 @@ func podioItem(clientId: String,
5470
5473
  - username: Your Apple ID Username
5471
5474
  - teamId: The ID of your App Store Connect team if you're in multiple teams
5472
5475
  - teamName: The name of your App Store Connect team if you're in multiple teams
5476
+ - platform: The platform to use (optional)
5473
5477
  - defaultRuleLevel: The default rule level unless otherwise configured
5474
5478
  - includeInAppPurchases: Should check in-app purchases?
5475
5479
  - freeStuffInIap: using text indicating that your IAP is free
@@ -5482,6 +5486,7 @@ func precheck(appIdentifier: Any = precheckfile.appIdentifier,
5482
5486
  username: Any = precheckfile.username,
5483
5487
  teamId: Any? = precheckfile.teamId,
5484
5488
  teamName: Any? = precheckfile.teamName,
5489
+ platform: Any = precheckfile.platform,
5485
5490
  defaultRuleLevel: Any = precheckfile.defaultRuleLevel,
5486
5491
  includeInAppPurchases: Bool = precheckfile.includeInAppPurchases,
5487
5492
  freeStuffInIap: Any? = precheckfile.freeStuffInIap)
@@ -5490,6 +5495,7 @@ func precheck(appIdentifier: Any = precheckfile.appIdentifier,
5490
5495
  RubyCommand.Argument(name: "username", value: username),
5491
5496
  RubyCommand.Argument(name: "team_id", value: teamId),
5492
5497
  RubyCommand.Argument(name: "team_name", value: teamName),
5498
+ RubyCommand.Argument(name: "platform", value: platform),
5493
5499
  RubyCommand.Argument(name: "default_rule_level", value: defaultRuleLevel),
5494
5500
  RubyCommand.Argument(name: "include_in_app_purchases", value: includeInAppPurchases),
5495
5501
  RubyCommand.Argument(name: "free_stuff_in_iap", value: freeStuffInIap)])
@@ -7431,7 +7437,7 @@ func supply(packageName: String,
7431
7437
  releaseStatus: String = "completed",
7432
7438
  track: String = "production",
7433
7439
  rollout: String? = nil,
7434
- metadataPath: String? = nil,
7440
+ metadataPath: String = "./metadata",
7435
7441
  key: String? = nil,
7436
7442
  issuer: String? = nil,
7437
7443
  jsonKey: String? = nil,
@@ -8588,7 +8594,7 @@ func uploadToPlayStore(packageName: String,
8588
8594
  releaseStatus: String = "completed",
8589
8595
  track: String = "production",
8590
8596
  rollout: String? = nil,
8591
- metadataPath: String? = nil,
8597
+ metadataPath: String = "./metadata",
8592
8598
  key: String? = nil,
8593
8599
  issuer: String? = nil,
8594
8600
  jsonKey: String? = nil,
@@ -9118,7 +9124,7 @@ func xcov(workspace: String? = nil,
9118
9124
  coverallsServiceJobId: String? = nil,
9119
9125
  coverallsRepoToken: String? = nil,
9120
9126
  xcconfig: String? = nil,
9121
- ideFoundationPath: String = "/Applications/Xcode-12.beta.5.app/Contents/Developer/../Frameworks/IDEFoundation.framework/Versions/A/IDEFoundation",
9127
+ ideFoundationPath: String = "/Applications/Xcode.app/Contents/Developer/../Frameworks/IDEFoundation.framework/Versions/A/IDEFoundation",
9122
9128
  legacySupport: Bool = false)
9123
9129
  {
9124
9130
  let command = RubyCommand(commandID: "", methodName: "xcov", className: nil, args: [RubyCommand.Argument(name: "workspace", value: workspace),
@@ -9254,14 +9260,14 @@ func parseInt(fromString: String, function: String = #function) -> Int {
9254
9260
  return NSString(string: fromString.trimmingCharacters(in: .punctuationCharacters)).integerValue
9255
9261
  }
9256
9262
 
9257
- let deliverfile: Deliverfile = Deliverfile()
9258
- let gymfile: Gymfile = Gymfile()
9259
- let matchfile: Matchfile = Matchfile()
9260
- let precheckfile: Precheckfile = Precheckfile()
9261
- let scanfile: Scanfile = Scanfile()
9262
- let screengrabfile: Screengrabfile = Screengrabfile()
9263
- let snapshotfile: Snapshotfile = Snapshotfile()
9263
+ let deliverfile = Deliverfile()
9264
+ let gymfile = Gymfile()
9265
+ let matchfile = Matchfile()
9266
+ let precheckfile = Precheckfile()
9267
+ let scanfile = Scanfile()
9268
+ let screengrabfile = Screengrabfile()
9269
+ let snapshotfile = Snapshotfile()
9264
9270
 
9265
9271
  // Please don't remove the lines below
9266
9272
  // They are used to detect outdated files
9267
- // FastlaneRunnerAPIVersion [0.9.88]
9273
+ // FastlaneRunnerAPIVersion [0.9.93]
@@ -14,4 +14,4 @@ class Gymfile: GymfileProtocol {
14
14
  // during the `init` process, and you won't see this message
15
15
  }
16
16
 
17
- // Generated with fastlane 2.157.0
17
+ // Generated with fastlane 2.158.0
@@ -181,4 +181,4 @@ extension GymfileProtocol {
181
181
 
182
182
  // Please don't remove the lines below
183
183
  // They are used to detect outdated files
184
- // FastlaneRunnerAPIVersion [0.9.38]
184
+ // FastlaneRunnerAPIVersion [0.9.43]
@@ -14,4 +14,4 @@ class Matchfile: MatchfileProtocol {
14
14
  // during the `init` process, and you won't see this message
15
15
  }
16
16
 
17
- // Generated with fastlane 2.157.0
17
+ // Generated with fastlane 2.158.0
@@ -165,4 +165,4 @@ extension MatchfileProtocol {
165
165
 
166
166
  // Please don't remove the lines below
167
167
  // They are used to detect outdated files
168
- // FastlaneRunnerAPIVersion [0.9.32]
168
+ // FastlaneRunnerAPIVersion [0.9.37]
@@ -14,4 +14,4 @@ class Precheckfile: PrecheckfileProtocol {
14
14
  // during the `init` process, and you won't see this message
15
15
  }
16
16
 
17
- // Generated with fastlane 2.157.0
17
+ // Generated with fastlane 2.158.0
@@ -11,6 +11,9 @@ protocol PrecheckfileProtocol: class {
11
11
  /// The name of your App Store Connect team if you're in multiple teams
12
12
  var teamName: String? { get }
13
13
 
14
+ /// The platform to use (optional)
15
+ var platform: String { get }
16
+
14
17
  /// The default rule level unless otherwise configured
15
18
  var defaultRuleLevel: String { get }
16
19
 
@@ -26,6 +29,7 @@ extension PrecheckfileProtocol {
26
29
  var username: String { return "" }
27
30
  var teamId: String? { return nil }
28
31
  var teamName: String? { return nil }
32
+ var platform: String { return "ios" }
29
33
  var defaultRuleLevel: String { return "error" }
30
34
  var includeInAppPurchases: Bool { return true }
31
35
  var freeStuffInIap: String? { return nil }
@@ -33,4 +37,4 @@ extension PrecheckfileProtocol {
33
37
 
34
38
  // Please don't remove the lines below
35
39
  // They are used to detect outdated files
36
- // FastlaneRunnerAPIVersion [0.9.31]
40
+ // FastlaneRunnerAPIVersion [0.9.36]
@@ -14,4 +14,4 @@ class Scanfile: ScanfileProtocol {
14
14
  // during the `init` process, and you won't see this message
15
15
  }
16
16
 
17
- // Generated with fastlane 2.157.0
17
+ // Generated with fastlane 2.158.0
@@ -257,4 +257,4 @@ extension ScanfileProtocol {
257
257
 
258
258
  // Please don't remove the lines below
259
259
  // They are used to detect outdated files
260
- // FastlaneRunnerAPIVersion [0.9.43]
260
+ // FastlaneRunnerAPIVersion [0.9.48]
@@ -14,4 +14,4 @@ class Screengrabfile: ScreengrabfileProtocol {
14
14
  // during the `init` process, and you won't see this message
15
15
  }
16
16
 
17
- // Generated with fastlane 2.157.0
17
+ // Generated with fastlane 2.158.0
@@ -93,4 +93,4 @@ extension ScreengrabfileProtocol {
93
93
 
94
94
  // Please don't remove the lines below
95
95
  // They are used to detect outdated files
96
- // FastlaneRunnerAPIVersion [0.9.33]
96
+ // FastlaneRunnerAPIVersion [0.9.38]
@@ -14,4 +14,4 @@ class Snapshotfile: SnapshotfileProtocol {
14
14
  // during the `init` process, and you won't see this message
15
15
  }
16
16
 
17
- // Generated with fastlane 2.157.0
17
+ // Generated with fastlane 2.158.0
@@ -181,4 +181,4 @@ extension SnapshotfileProtocol {
181
181
 
182
182
  // Please don't remove the lines below
183
183
  // They are used to detect outdated files
184
- // FastlaneRunnerAPIVersion [0.9.27]
184
+ // FastlaneRunnerAPIVersion [0.9.32]
@@ -52,6 +52,7 @@ module FastlaneCore
52
52
  status = FastlaneCore::FastlanePty.spawn(command) do |command_stdout, command_stdin, pid|
53
53
  command_stdout.each do |l|
54
54
  line = l.chomp
55
+ line = line[1..-1] if line[0] == "\r"
55
56
  output << line
56
57
 
57
58
  next unless print_all
@@ -18,18 +18,18 @@ module Match
18
18
  UI.important("More information https://docs.fastlane.tools/actions/match/#access-control")
19
19
  end
20
20
 
21
+ # Prompts select team if multiple teams and none specified
21
22
  UI.message("Verifying that the certificate and profile are still valid on the Dev Portal...")
22
- Spaceship.login(user)
23
- Spaceship.select_team(team_id: team_id, team_name: team_name)
23
+ Spaceship::ConnectAPI.login(user, use_portal: true, use_tunes: false, portal_team_id: team_id, team_name: team_name)
24
24
  end
25
25
 
26
26
  # The team ID of the currently logged in team
27
27
  def team_id
28
- return Spaceship.client.team_id
28
+ return Spaceship::ConnectAPI.client.portal_team_id
29
29
  end
30
30
 
31
31
  def bundle_identifier_exists(username: nil, app_identifier: nil, platform: nil)
32
- found = Spaceship.app.find(app_identifier, mac: platform == "macos")
32
+ found = Spaceship::ConnectAPI::BundleId.find(app_identifier)
33
33
  return if found
34
34
 
35
35
  require 'sigh/runner'
@@ -39,7 +39,7 @@ module Match
39
39
  })
40
40
  UI.error("An app with that bundle ID needs to exist in order to create a provisioning profile for it")
41
41
  UI.error("================================================================")
42
- available_apps = Spaceship.app.all.collect { |a| "#{a.bundle_id} (#{a.name})" }
42
+ available_apps = Spaceship::ConnectAPI::BundleId.all.collect { |a| "#{a.identifier} (#{a.name})" }
43
43
  UI.message("Available apps:\n- #{available_apps.join("\n- ")}")
44
44
  UI.error("Make sure to run `fastlane match` with the same user and team every time.")
45
45
  UI.user_error!("Couldn't find bundle identifier '#{app_identifier}' for the user '#{username}'")
@@ -364,10 +364,7 @@ module Pilot
364
364
  begin
365
365
  team = tunes_client.teams.find { |t| t['contentProvider']['contentProviderId'].to_s == tunes_client.team_id }
366
366
  name = team['contentProvider']['name']
367
- STDERR.puts("name: #{name}")
368
- STDERR.puts("id: #{generic_transporter.provider_ids}")
369
367
  provider_id = generic_transporter.provider_ids[name]
370
- STDERR.puts("provider_id: #{provider_id}")
371
368
  UI.verbose("Inferred provider id #{provider_id} for team #{name}.")
372
369
  return FastlaneCore::ItunesTransporter.new(options[:username], nil, false, provider_id)
373
370
  rescue => ex
@@ -24,7 +24,7 @@ module Pilot
24
24
  config[:username] ||= CredentialsManager::AppfileConfig.try_fetch_value(:apple_id)
25
25
 
26
26
  UI.message("Login to App Store Connect (#{config[:username]})")
27
- Spaceship::ConnectAPI.login(config[:username], team_id: config[:team_id], team_name: config[:team_name])
27
+ Spaceship::ConnectAPI.login(config[:username], use_portal: false, use_tunes: true, tunes_team_id: config[:team_id], team_name: config[:team_name])
28
28
  UI.message("Login successful")
29
29
  end
30
30
  end
@@ -60,6 +60,15 @@ module Precheck
60
60
  verify_block: proc do |value|
61
61
  ENV["FASTLANE_ITC_TEAM_NAME"] = value.to_s
62
62
  end),
63
+ FastlaneCore::ConfigItem.new(key: :platform,
64
+ short_option: "-j",
65
+ env_name: "PRECHECK_PLATFORM",
66
+ description: "The platform to use (optional)",
67
+ optional: true,
68
+ default_value: "ios",
69
+ verify_block: proc do |value|
70
+ UI.user_error!("The platform can only be ios, appletvos, or osx") unless %('ios', 'appletvos', 'osx').include?(value)
71
+ end),
63
72
  FastlaneCore::ConfigItem.new(key: :default_rule_level,
64
73
  short_option: "-r",
65
74
  env_name: "PRECHECK_DEFAULT_RULE_LEVEL",
@@ -1,4 +1,5 @@
1
1
  require 'spaceship/tunes/language_item'
2
+ require 'spaceship/tunes/iap_list'
2
3
  require 'fastlane/markdown_table_formatter'
3
4
 
4
5
  require_relative 'module'
@@ -43,8 +44,8 @@ module Precheck
43
44
  class RuleProcessor
44
45
  def self.process_app_and_version(app: nil, app_version: nil, rules: nil)
45
46
  items_to_check = []
46
- items_to_check += generate_text_items_to_check(app: app, app_version: app_version)
47
- items_to_check += generate_url_items_to_check(app: app, app_version: app_version)
47
+ items_to_check += generate_app_items_to_check(app: app)
48
+ items_to_check += generate_version_items_to_check(app_version: app_version)
48
49
 
49
50
  return process_rules(items_to_check: items_to_check, rules: rules)
50
51
  end
@@ -125,66 +126,41 @@ module Precheck
125
126
  return rule_hash
126
127
  end
127
128
 
128
- def self.generate_url_items_to_check(app: nil, app_version: nil)
129
+ def self.generate_app_items_to_check(app: nil)
129
130
  items = []
130
- items += collect_urls_from_hash(hash: app_version.support_url,
131
- item_name: :support_url,
132
- friendly_name_postfix: "support URL")
133
- items += collect_urls_from_hash(hash: app_version.marketing_url,
134
- item_name: :marketing_url,
135
- friendly_name_postfix: "marketing URL",
136
- is_optional: true)
137
-
138
- items += collect_urls_from_hash(hash: app.details.privacy_url,
139
- item_name: :privacy_url,
140
- friendly_name_postfix: "privacy URL",
141
- is_optional: true)
142
- return items
143
- end
144
131
 
145
- def self.collect_urls_from_hash(hash: nil, item_name: nil, friendly_name_postfix: nil, is_optional: false)
146
- items = []
147
- hash.each do |key, value|
148
- items << URLItemToCheck.new(value, item_name, "#{friendly_name_postfix}: (#{key})", is_optional)
132
+ # App info localizations
133
+ app_info = app.fetch_edit_app_info
134
+ app_info_localizations = app_info.get_app_info_localizations
135
+ app_info_localizations.each do |localization|
136
+ items << collect_text_items_from_language_item(locale: localization.locale,
137
+ value: localization.name,
138
+ item_name: :app_name,
139
+ friendly_name_postfix: "app name")
140
+
141
+ items << collect_text_items_from_language_item(locale: localization.locale,
142
+ value: localization.subtitle,
143
+ item_name: :app_subtitle,
144
+ friendly_name_postfix: "app name subtitle",
145
+ is_optional: true)
146
+
147
+ items << collect_text_items_from_language_item(locale: localization.locale,
148
+ value: localization.privacy_policy_text,
149
+ item_name: :privacy_policy_text,
150
+ friendly_name_postfix: " tv privacy policy")
151
+
152
+ items << collect_urls_from_language_item(locale: localization.locale,
153
+ value: localization.privacy_policy_url,
154
+ item_name: :privacy_policy_url,
155
+ friendly_name_postfix: "privacy URL",
156
+ is_optional: true)
149
157
  end
150
- return items
151
- end
152
-
153
- def self.generate_text_items_to_check(app: nil, app_version: nil)
154
- items = []
155
-
156
- items << TextItemToCheck.new(app_version.copyright, :copyright, "copyright")
157
-
158
- items += collect_text_items_from_language_item(hash: app_version.keywords,
159
- item_name: :keywords,
160
- friendly_name_postfix: "keywords")
161
-
162
- items += collect_text_items_from_language_item(hash: app_version.description,
163
- item_name: :description,
164
- friendly_name_postfix: "description")
165
-
166
- items += collect_text_items_from_language_item(hash: app_version.release_notes,
167
- item_name: :release_notes,
168
- friendly_name_postfix: "release notes")
169
-
170
- items += collect_text_items_from_language_item(hash: app.details.name,
171
- item_name: :app_name,
172
- friendly_name_postfix: "app name")
173
-
174
- items += collect_text_items_from_language_item(hash: app.details.apple_tv_privacy_policy,
175
- item_name: :app_subtitle,
176
- friendly_name_postfix: " tv privacy policy")
177
-
178
- items += collect_text_items_from_language_item(hash: app.details.subtitle,
179
- item_name: :app_subtitle,
180
- friendly_name_postfix: "app name subtitle",
181
- is_optional: true)
182
158
 
183
159
  should_include_iap = Precheck.config[:include_in_app_purchases]
184
160
  if should_include_iap
185
161
  UI.message("Reading in-app purchases. If you have a lot, this might take a while")
186
162
  UI.message("You can disable IAP checking by setting the `include_in_app_purchases` flag to `false`")
187
- in_app_purchases = app.in_app_purchases.all
163
+ in_app_purchases = get_iaps(app_id: app.id)
188
164
  in_app_purchases ||= []
189
165
  in_app_purchases.each do |purchase|
190
166
  items += collect_iap_language_items(purchase_edit_versions: purchase.edit.versions)
@@ -195,6 +171,64 @@ module Precheck
195
171
  return items
196
172
  end
197
173
 
174
+ def self.generate_version_items_to_check(app_version: nil)
175
+ items = []
176
+
177
+ items << TextItemToCheck.new(app_version.copyright, :copyright, "copyright")
178
+
179
+ # Version localizations
180
+ version_localizations = app_version.get_app_store_version_localizations
181
+ version_localizations.each do |localization|
182
+ items << collect_text_items_from_language_item(locale: localization.locale,
183
+ value: localization.keywords,
184
+ item_name: :keywords,
185
+ friendly_name_postfix: "keywords")
186
+
187
+ items << collect_text_items_from_language_item(locale: localization.locale,
188
+ value: localization.description,
189
+ item_name: :description,
190
+ friendly_name_postfix: "description")
191
+
192
+ items << collect_text_items_from_language_item(locale: localization.locale,
193
+ value: localization.whats_new,
194
+ item_name: :release_notes,
195
+ friendly_name_postfix: "what's new")
196
+
197
+ items << collect_urls_from_language_item(locale: localization.locale,
198
+ value: localization.support_url,
199
+ item_name: :support_url,
200
+ friendly_name_postfix: "support URL")
201
+
202
+ items << collect_urls_from_language_item(locale: localization.locale,
203
+ value: localization.marketing_url,
204
+ item_name: :marketing_url,
205
+ friendly_name_postfix: "marketing URL",
206
+ is_optional: true)
207
+ end
208
+
209
+ return items
210
+ end
211
+
212
+ # As of 2020-09-04, this is the only non App Store Connect call in prechecks
213
+ # This will need to get replaced when the API becomes available
214
+ def self.get_iaps(app_id: nil, include_deleted: false)
215
+ r = Spaceship::Tunes.client.iaps(app_id: app_id)
216
+ return_iaps = []
217
+ r.each do |product|
218
+ attrs = product
219
+
220
+ # This is not great but Spaceship::Tunes::IAPList.factory looks
221
+ # for `application.apple_id`
222
+ mock_application = OpenStruct.new({ apple_id: app_id })
223
+ attrs[:application] = mock_application
224
+
225
+ loaded_iap = Spaceship::Tunes::IAPList.factory(attrs)
226
+ next if loaded_iap.status == "deleted" && !include_deleted
227
+ return_iaps << loaded_iap
228
+ end
229
+ return return_iaps
230
+ end
231
+
198
232
  def self.collect_iap_language_items(purchase_edit_versions: nil, is_optional: false)
199
233
  items = []
200
234
  purchase_edit_versions.each do |language_key, hash|
@@ -207,12 +241,12 @@ module Precheck
207
241
  end
208
242
 
209
243
  # a few attributes are LanguageItem this method creates a TextItemToCheck for each pair
210
- def self.collect_text_items_from_language_item(hash: nil, item_name: nil, friendly_name_postfix: nil, is_optional: false)
211
- items = []
212
- hash.each do |key, value|
213
- items << TextItemToCheck.new(value, item_name, "#{friendly_name_postfix}: (#{key})", is_optional)
214
- end
215
- return items
244
+ def self.collect_text_items_from_language_item(locale: nil, value: nil, item_name: nil, friendly_name_postfix: nil, is_optional: false)
245
+ return TextItemToCheck.new(value, item_name, "#{friendly_name_postfix}: (#{locale})", is_optional)
246
+ end
247
+
248
+ def self.collect_urls_from_language_item(locale: nil, value: nil, item_name: nil, friendly_name_postfix: nil, is_optional: false)
249
+ return URLItemToCheck.new(value, item_name, "#{friendly_name_postfix}: (#{locale})", is_optional)
216
250
  end
217
251
  end
218
252
  end