xcode-utils 1.0.1 → 1.0.6

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: f1970acf585e3734341653767ceaeaf65d2b16af18d4e2cb08e6c0f69166abe2
4
- data.tar.gz: 810661aa622d73e943a9a75c91c92225ca2c40a57e4868eb968b99a7ac336eb1
3
+ metadata.gz: '078c1054432a4dfb2ccd967637b74aa4cbc2aabdb67c80d000361c2407987694'
4
+ data.tar.gz: 3bd681d4b310c1f961bb9f85263965c44e73185f41cfa2a24310d987b7babb90
5
5
  SHA512:
6
- metadata.gz: 56858946daecab5390cdcefd1d8946fe9e8a05b8cbec5e50f09f7410ecf335d0fa29bd312de883c7afa2442664a5705fa5f969836e1c68f5d2abc0b8ae3bd804
7
- data.tar.gz: 6bacf895b66a53c1eb09220a03e52378ccf9d6510dc2560fd4371c1a579826ece7ccfb3f2e8ad71041d9a1e4b8b3e3b0c5681f4408221e088e05f4b776accba2
6
+ metadata.gz: 654da996344614593d38fab2a17f90abd2e1a7342fcdf74b55aa1defbf2f7315005c7ea501d00a78cc12400d2a9eaa2992be3c924dff143de88332584359b211
7
+ data.tar.gz: 449501e3a2db25ede86c450c0437eec792893c4bf5a82ccd7595bb7f2a158a7f59aa1fdfab7b6af82dbe0ac04519bebe668698e197834df57df33cadde9e1341
data/README.md CHANGED
@@ -9,6 +9,7 @@ $ gem install xcode-utils
9
9
  ```
10
10
 
11
11
  ## UITestRunner
12
+ Make available single test page in app as standalone
12
13
 
13
14
  ### Install UITestRunner in your xcode project
14
15
  ```
@@ -121,4 +122,4 @@ $ xcutils carthage clean
121
122
 
122
123
  This project is licensed under the terms of the MIT license. See the [LICENSE](LICENSE) file.
123
124
 
124
- > This project and all fastlane tools are in no way affiliated with Apple Inc or Google. This project is open source under the MIT license, which means you have full access to the source code and can modify it to fit your own needs. All fastlane tools run on your own computer or server, so your credentials or other sensitive information will never leave your own computer. You are responsible for how you use fastlane tools.
125
+ > This project and all fastlane tools are in no way affiliated with Apple Inc or Google. This project is open source under the MIT license, which means you have full access to the source code and can modify it to fit your own needs. All fastlane tools run on your own computer or server, so your credentials or other sensitive information will never leave your own computer. You are responsible for how you use fastlane tools.
@@ -1,5 +1,5 @@
1
1
  require 'xcodeproj'
2
- require 'xcutils/carthage/colors'
2
+ require 'xcutils/colors'
3
3
 
4
4
  module XcodeUtils
5
5
  module Carthage
@@ -24,13 +24,13 @@ module XcodeUtils
24
24
 
25
25
  def open_project
26
26
  if !Dir.exist?(@build_path)
27
- abort("😭 The Carthage build has not yet been successful. Please try again after successful arthage build.")
27
+ abort "😭 The Carthage build has not yet been successful. Please try again after successful arthage build.".red
28
28
  end
29
29
 
30
30
  project_names = Dir["./*.xcodeproj"]
31
31
 
32
32
  if project_names.first.nil?
33
- abort("😭 Does not exist project to configure.")
33
+ abort "😭 Does not exist project to configure.".red
34
34
  end
35
35
 
36
36
  puts "💎💎 Project Found -> #{project_names.first} 💎💎"
@@ -1,6 +1,7 @@
1
1
  require 'xcodeproj'
2
2
  require 'plist'
3
3
  require 'nokogiri'
4
+ require 'xcutils/colors'
4
5
 
5
6
  module XcodeUtils
6
7
  class Command
@@ -14,15 +15,15 @@ module XcodeUtils
14
15
 
15
16
  self.arguments = [
16
17
  CLAide::Argument.new('PROJECT_NAME', :true),
17
- CLAide::Argument.new('BASE_CONFIG_NAME', :true),
18
- CLAide::Argument.new('BASE_SCHEME_NAME', :true)
18
+ CLAide::Argument.new('TARGET_CONFIG_NAME', :true),
19
+ CLAide::Argument.new('TARGET_SCHEME_NAME', :true)
19
20
  ]
20
21
 
21
22
  def self.options
22
23
  [
23
- ['--project-name=""', 'The name of your xcode project'],
24
- ['--target-config=""', 'The name of build configuration to be copied to uitestrunner build configuration'],
25
- ['--target-scheme=""', 'The name of build scheme to be copied to uitestrunner build scheme'],
24
+ ['--project-name', 'The name of your xcode project'],
25
+ ['--target-config', 'The name of build configuration to be copied to uitestrunner build configuration'],
26
+ ['--target-scheme', 'The name of build scheme to be copied to uitestrunner build scheme'],
26
27
  ]
27
28
  end
28
29
 
@@ -44,100 +45,152 @@ module XcodeUtils
44
45
  end
45
46
 
46
47
  def run
47
- generate_build_configuration
48
- generate_scheme
48
+ puts "🤖 Run: project_name: #{@project_name}, target_config: #{@taget_config}, target_scheme: #{@target_scheme}".green
49
+ open_project
50
+ generate_project_configuration
51
+ generate_build_configurations
52
+ generate_scheme_files
49
53
  copy_template_files
54
+
55
+ if !@project.nil?
56
+ puts "Save project".green
57
+ @project.save()
58
+ puts "🤩 Finished".green
59
+ else
60
+ puts "😡 Aborted".red
61
+ end
50
62
  end
51
-
52
- def generate_build_configuration
53
- puts "Input: project_name: #{@project_name}, target_config: #{@taget_config}, target_scheme: #{@target_scheme}"
63
+
64
+ def open_project
65
+ puts "Open project #{@project_name}"
66
+
67
+ if !Dir.exist?(@project_path)
68
+ abort "😭 Abort to install. Project #{project_name} does not exist".red
69
+ end
70
+ @project = Xcodeproj::Project.open(@project_path)
71
+ end
72
+
73
+ def generate_project_configuration
74
+ puts "Generating project configuration #{@uitest_name} into #{@project_name}"
54
75
 
55
- project = Xcodeproj::Project.open(@project_path)
56
- configuration_list = project.root_object.build_configuration_list
76
+ configuration_list = @project.root_object.build_configuration_list
57
77
 
58
78
  if configuration_list.build_settings(@uitest_name) != nil
59
- puts "uitest already install in the project #{@project_name}"
79
+ puts "\tSkip to generate project configuration for #{@uitest_name}. It is already installed in the project #{@project_name}".gray
60
80
  return
61
81
  end
62
82
 
63
- puts "Initializing #{@uitest_name}"
64
- puts "Generating project configuration"
65
-
66
- configuration = project.new(Xcodeproj::Project::Object::XCBuildConfiguration)
83
+ configuration = @project.new(Xcodeproj::Project::Object::XCBuildConfiguration)
67
84
  configuration.name = @uitest_name
68
85
  configuration.build_settings = configuration_list.build_settings(@taget_config)
69
86
  configuration_list.build_configurations << configuration
87
+ end
88
+
89
+ def generate_build_configurations
90
+ puts "Generating build configurations"
70
91
 
71
- project.targets.each do |target|
72
- break if target.build_configurations.select { |e| e.name == @uitest_name }.count > 0
73
-
74
- puts "Generating build configuration #{target.name}:#{@uitest_name}"
75
-
76
- base_config = target.build_configurations.select { |e| e.name == @taget_config }.first
77
- org_main_storyboard_file = nil
92
+ @project.targets.each { |target|
93
+ target_config = target.build_configurations.select { |e| e.name == @taget_config }.first
94
+ target_main_sb = nil
78
95
 
79
96
  target.build_configurations.each { |e|
97
+ break if e.name == @uitest_name
98
+
99
+ puts "\tConfigure build configuration #{e.name} in #{target.name}"
100
+
80
101
  path = e.build_settings['INFOPLIST_FILE']
81
- obj = Plist.parse_xml(path)
82
- var_name = '$(MAIN_STORYBOARD_FILE)'
83
- e.build_settings['MAIN_STORYBOARD_FILE'] = obj['UIMainStoryboardFile'] != var_name ? obj['UIMainStoryboardFile'] : org_main_storyboard_file
84
- obj['UIMainStoryboardFile'] = '$(MAIN_STORYBOARD_FILE)'
85
-
86
- if org_main_storyboard_file == nil
87
- org_main_storyboard_file = e.build_settings['MAIN_STORYBOARD_FILE']
102
+ plist = Plist.parse_xml(path)
103
+ plist_main_sb = plist['UIMainStoryboardFile']
104
+ build_settings_main_sb = e.build_settings['MAIN_STORYBOARD_FILE']
105
+ variable_name = '$(MAIN_STORYBOARD_FILE)'
106
+ is_not_variable = plist_main_sb != variable_name
107
+
108
+ e.build_settings['MAIN_STORYBOARD_FILE'] = is_not_variable ? plist_main_sb : (target_main_sb != nil ? target_main_sb : build_settings_main_sb)
109
+
110
+ if target_main_sb.nil?
111
+ target_main_sb = build_settings_main_sb
88
112
  end
113
+
114
+ plist['UIMainStoryboardFile'] = variable_name
89
115
 
90
- File.write(path, obj.to_plist)
116
+ if is_not_variable
117
+ File.write(path, plist.to_plist)
118
+ end
119
+
120
+ file_names_string = e.build_settings['EXCLUDED_SOURCE_FILE_NAMES']
121
+ file_names_string = appended(file_names_string, '$(SRCROOT)/$(PRODUCT_NAME)/UITestRunner/*')
122
+ file_names_string = appended(file_names_string, '$(SRCROOT)/$(PRODUCT_NAME)/UITestRunner/**/*')
123
+ e.build_settings['EXCLUDED_SOURCE_FILE_NAMES'] = file_names_string
91
124
  }
92
-
93
- new_config = project.new(Xcodeproj::Project::Object::XCBuildConfiguration)
94
- new_config.name = @uitest_name
95
- new_config.base_configuration_reference = base_config.base_configuration_reference
96
- new_config.build_settings.update(base_config.build_settings)
125
+
126
+ test_config = target.build_configurations.select { |e| e.name == @uitest_name }.first
127
+
128
+ if test_config.nil?
129
+ puts "\tGenerating build configuration #{@uitest_name} into #{target.name}"
130
+ new_config = @project.new(Xcodeproj::Project::Object::XCBuildConfiguration)
131
+ new_config.name = @uitest_name
132
+ new_config.base_configuration_reference = target_config.base_configuration_reference
133
+ target.build_configurations << new_config
134
+ else
135
+ puts "\tConfigure build configuration #{@uitest_name} in #{target.name}"
136
+ new_config = test_config
137
+ end
138
+
139
+ new_config.build_settings.update(target_config.build_settings)
97
140
  new_config.build_settings['MAIN_STORYBOARD_FILE'] = @uitest_name
141
+ new_config.build_settings['EXCLUDED_SOURCE_FILE_NAMES'] = nil
142
+ }
143
+ end
144
+
145
+ def generate_scheme_files
146
+ puts "Generating scheme files"
98
147
 
99
- target.build_configurations << new_config
148
+ @project.targets.each { |target|
149
+ scheme_name = "#{target.name} #{@uitest_name}"
150
+
151
+ if File.exist?(scheme_path(scheme_name))
152
+ puts "\tSkip to generate. A scheme file is already exsit, #{scheme_name}".gray
153
+ next
154
+ end
100
155
 
101
- puts "Generating scheme #{target.name} #{@uitest_name}"
102
-
103
- project.save()
104
- end
105
- end
156
+ puts "\tGenerating scheme file #{scheme_path(scheme_name)}"
106
157
 
107
- def generate_scheme
108
- scheme_name = "#{@project_name} #{@uitest_name}"
109
-
110
- FileUtils.copy_file(scheme_path(@target_scheme), scheme_path(scheme_name))
111
-
112
- scheme = Xcodeproj::XCScheme.new(scheme_path(scheme_name))
113
- scheme.launch_action.build_configuration = @uitest_name
114
- scheme.save_as(@project_path, scheme_name)
158
+ FileUtils.copy_file(scheme_path(@target_scheme), scheme_path(scheme_name))
159
+
160
+ scheme = Xcodeproj::XCScheme.new(scheme_path(scheme_name))
161
+ scheme.launch_action.build_configuration = @uitest_name
162
+ scheme.save_as(@project_path, scheme_name)
163
+ }
115
164
  end
116
165
 
117
166
  def copy_template_files
118
- template_path = "./#{@project_name}/#{@uitest_name}"
119
-
120
- if Dir.exist?(template_path)
121
- puts "Template files already exist in the project #{@project_name}"
122
- return
123
- end
124
-
125
- puts "Copying template files into project #{@project_name}"
126
-
127
- path = File.expand_path('../../../templates', __FILE__)
128
- FileUtils.copy_entry path, "./#{@project_name}"
129
-
130
- puts "Adding references for files and resources into project #{@project_name}"
131
-
132
- project = Xcodeproj::Project.open(@project_path)
133
-
134
- project.targets.each { |target|
135
- target_group = project.groups.select { |e| e.path == target.name }.first
136
- template_group = target_group.new_group(nil, @uitest_name)
137
- add_files("#{template_path}/*", template_group, target)
167
+ puts "Copy template files"
168
+
169
+ @project.targets.each { |target|
170
+ template_path = "./#{target.name}/#{@uitest_name}"
171
+
172
+ if !Dir.exist?(template_path)
173
+ puts "\tCopying template files into target #{target.name}"
174
+ path = File.expand_path('../../../templates', __FILE__)
175
+ FileUtils.copy_entry path, "./#{target.name}"
176
+ else
177
+ puts "\tSkip to copy template files. Files are already exsit".gray
178
+ end
179
+
180
+ target_group = @project.groups.select { |e| e.path == target.name }.first
181
+
182
+ if target_group.groups.select { |e| e.path == @uitest_name }.first.nil?
183
+ puts "\tAdding references for files and resources into target #{target.name}"
184
+ template_group = target_group.new_group(nil, @uitest_name)
185
+ add_files("#{template_path}/*", template_group, target)
186
+ end
138
187
  }
139
-
140
- project.save()
188
+ end
189
+
190
+ def appended(string, other)
191
+ return other if string == nil
192
+ return string if string.include? other
193
+ return string << " #{other}"
141
194
  end
142
195
 
143
196
  def add_files(direc, current_group, main_target)
@@ -157,6 +210,8 @@ module XcodeUtils
157
210
  if item.include? ".storyboard" or item.include? ".xib"
158
211
  set_custom_module(item)
159
212
  main_target.add_resources([i])
213
+ else
214
+ main_target.add_resources([i])
160
215
  end
161
216
  end
162
217
  end
@@ -1,3 +1,3 @@
1
1
  module XcodeUtils
2
- VERSION = '1.0.1'.freeze
2
+ VERSION = '1.0.6'.freeze
3
3
  end
@@ -3,12 +3,10 @@
3
3
  // Copyright © 2020 abc-studio. All rights reserved.
4
4
  //
5
5
 
6
- #if DEBUG
7
6
  protocol UITestAuthorizationProvider {
8
7
  var hasAccessToken: Bool {get}
9
8
  var hasRefreshToken: Bool {get}
10
9
  func refreshToken(completion: @escaping () -> Void)
11
10
  func signIn(_ parent: UIViewController, completion: @escaping () -> Void)
12
11
  func signOut()
13
- }
14
- #endif
12
+ }
@@ -3,7 +3,6 @@
3
3
  // Copyright © 2020 abc-studio. All rights reserved.
4
4
  //
5
5
 
6
- #if DEBUG
7
6
  import Foundation
8
7
 
9
8
  protocol UITestSuiteInitializable {
@@ -20,13 +19,14 @@ class UITestSuite: UITestSuiteInitializable {
20
19
 
21
20
  static var authorizationProvider: UITestAuthorizationProvider?
22
21
 
23
- var isNewSession = false
24
- var useLogin = true
25
- var testRunnerViewController: UITestRunnerViewController! {
22
+ weak var testRunnerViewController: UITestRunnerViewController! {
26
23
  didSet {
27
24
  setUp()
28
25
  }
29
26
  }
27
+
28
+ var isNewSession = false
29
+ var useLogin = true
30
30
  var view: UIView {
31
31
  return testRunnerViewController.view
32
32
  }
@@ -62,7 +62,7 @@ class UITestSuite: UITestSuiteInitializable {
62
62
  logout()
63
63
  signIn()
64
64
  } else {
65
- Self.authorizationProvider?.refreshAccessToken {
65
+ Self.authorizationProvider?.refreshToken {
66
66
  self.runTests()
67
67
  }
68
68
  }
@@ -86,12 +86,16 @@ class UITestSuite: UITestSuiteInitializable {
86
86
  }
87
87
 
88
88
  extension UITestSuite {
89
+ func present(_ viewController: UIViewController, animated: Bool = false, completion: (() -> Void)? = nil) {
90
+ viewController.modalPresentationStyle = .fullScreen
91
+ testRunnerViewController.present(viewController, animated: animated, completion: completion)
92
+ }
93
+
89
94
  @discardableResult
90
- func present(_ viewController: UIViewController, completion: (() -> Void)? = nil) -> UINavigationController {
91
- let navigationController = UINavigationController(rootViewController: viewController)
95
+ func present(rootViewController: UIViewController, animated: Bool = false, completion: (() -> Void)? = nil) -> UINavigationController {
96
+ let navigationController = UINavigationController(rootViewController: rootViewController)
92
97
  navigationController.modalPresentationStyle = .fullScreen
93
- testRunnerViewController.present(navigationController, animated: false, completion: completion)
98
+ testRunnerViewController.present(navigationController, animated: animated, completion: completion)
94
99
  return navigationController
95
100
  }
96
- }
97
- #endif
101
+ }
@@ -3,7 +3,6 @@
3
3
  // Copyright © 2020 abc-studio. All rights reserved.
4
4
  //
5
5
 
6
- #if DEBUG
7
6
  import Foundation
8
7
 
9
8
  final class MainTestSuite: UITestSuite {
@@ -24,5 +23,4 @@ final class MainTestSuite: UITestSuite {
24
23
  private func testExample() {
25
24
  // This is an example of a functional test case.
26
25
  }
27
- }
28
- #endif
26
+ }
@@ -3,7 +3,6 @@
3
3
  // Copyright © 2020 abc-studio. All rights reserved.
4
4
  //
5
5
 
6
- #if DEBUG
7
6
  struct UITestAuthorizationProviderImpl: UITestAuthorizationProvider {
8
7
 
9
8
  // MARK: - Implementations of Protocol UITestAuthorizationProvider
@@ -23,5 +22,4 @@ struct UITestAuthorizationProviderImpl: UITestAuthorizationProvider {
23
22
 
24
23
  func signOut() {
25
24
  }
26
- }
27
- #endif
25
+ }
@@ -3,36 +3,39 @@
3
3
  // Copyright © 2020 abc-studio. All rights reserved.
4
4
  //
5
5
 
6
- #if DEBUG
7
6
  import UIKit
8
7
 
9
8
  final class UITestRunnerViewController: UIViewController {
10
9
 
10
+ // MARK: - Private Properties
11
+
12
+ private var suite: UITestSuite!
13
+
11
14
  // MARK: - Overridden: UIViewController
12
15
 
13
16
  override func viewDidLoad() {
14
17
  super.viewDidLoad()
15
18
 
16
- title = "UITestRunner"
17
-
18
19
  UITestSuite.authorizationProvider = UITestAuthorizationProviderImpl()
20
+ }
19
21
 
20
- runTestSuites()
22
+ override func viewDidAppear(_ animated: Bool) {
23
+ super.viewDidAppear(animated)
24
+
25
+ if children.count < 1 {
26
+ runTestSuites()
27
+ }
21
28
  }
22
-
23
- // MARK: - Private Properties
24
-
25
- private var suite: UITestSuite!
26
29
 
27
30
  // MARK: - Private Methods
28
31
 
29
32
  private func runTestSuites() {
30
33
  runTestSuite(MainTestSuite.self)
31
34
  }
35
+
32
36
  private func runTestSuite<T: UITestSuite>(_ suiteType: T.Type) {
33
37
  suite = suiteType.init()
34
38
  suite.testRunnerViewController = self
35
39
  suite.run()
36
40
  }
37
- }
38
- #endif
41
+ }
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: xcode-utils
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.0.1
4
+ version: 1.0.6
5
5
  platform: ruby
6
6
  authors:
7
7
  - Steve Kim
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2020-08-18 00:00:00.000000000 Z
11
+ date: 2020-08-21 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: claide
@@ -123,8 +123,8 @@ files:
123
123
  - bin/xcutils
124
124
  - lib/xcutils.rb
125
125
  - lib/xcutils/carthage.rb
126
- - lib/xcutils/carthage/colors.rb
127
126
  - lib/xcutils/carthage/xcconfig.rb
127
+ - lib/xcutils/colors.rb
128
128
  - lib/xcutils/command.rb
129
129
  - lib/xcutils/uitest.rb
130
130
  - lib/xcutils/version.rb