branch_io_cli 0.6.0 → 0.7.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +12 -4
- data/lib/assets/completions/completion.bash +1 -1
- data/lib/assets/completions/completion.zsh +1 -1
- data/lib/branch_io_cli/cli.rb +8 -5
- data/lib/branch_io_cli/commands/report_command.rb +98 -14
- data/lib/branch_io_cli/commands/setup_command.rb +5 -6
- data/lib/branch_io_cli/commands/validate_command.rb +2 -9
- data/lib/branch_io_cli/helper/configuration_helper.rb +20 -1
- data/lib/branch_io_cli/helper/ios_helper.rb +347 -169
- data/lib/branch_io_cli/version.rb +1 -1
- metadata +30 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: b12805e82fb366c82741249dfbe0b186dd453cd6
|
4
|
+
data.tar.gz: beed4c107749da36ab0c36d31dfb77d544a083e8
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 88ce57d3ee76c932ec1df8fea6befa753a864753f9d741d4b779b5d545e840b89af98a921e238f345a00878375678f707576185d9f22c14bdbd356c250e3057f
|
7
|
+
data.tar.gz: b5a0b49080a5213523461e43ee3595bfa7a874d7de528ce4eca98e6b15efa0d240d062ad475f33e35229efb9cdad5dadcf5e5fae32d7fa24bb808bd38ca9ef55
|
data/README.md
CHANGED
@@ -28,6 +28,7 @@ Note that this command may require `sudo` access if you are using the system Rub
|
|
28
28
|
branch_io -h
|
29
29
|
branch_io setup -h
|
30
30
|
branch_io validate -h
|
31
|
+
branch_io report -h
|
31
32
|
```
|
32
33
|
|
33
34
|
### Shell completion
|
@@ -103,10 +104,10 @@ Before using this command, make sure to set up your app in the [Branch Dashboard
|
|
103
104
|
- Domain name(s) used for Branch links
|
104
105
|
- Location of your Xcode project (may be inferred in simple projects)
|
105
106
|
|
106
|
-
|
107
|
-
|
108
|
-
|
109
|
-
|
107
|
+
If using the `--commit` option, `git` is required. If not using `--no-add-sdk`,
|
108
|
+
the `pod` or `carthage` command may be required. If not found, the CLI will
|
109
|
+
offer to install and set up these command-line tools for you. Alternately, you can arrange
|
110
|
+
that the relevant commands are available in your `PATH`.
|
110
111
|
|
111
112
|
#### Options
|
112
113
|
|
@@ -124,6 +125,7 @@ command, respectively, available in your path.
|
|
124
125
|
|--target MyAppTarget|Name of a target to modify in the Xcode project|
|
125
126
|
|--podfile /path/to/Podfile|Path to the Podfile for the project|
|
126
127
|
|--cartfile /path/to/Cartfile|Path to the Cartfile for the project|
|
128
|
+
|--carthage-command <command>|Command to use when installing from Carthage (default: update --platform ios)|
|
127
129
|
|--frameworks AdSupport,CoreSpotlight,SafariServices|Comma-separated list of system frameworks to add to the project|
|
128
130
|
|--[no-]pod-repo-update|Update the local podspec repo before installing (default: yes)|
|
129
131
|
|--[no-]validate|Validate Universal Link configuration (default: yes)|
|
@@ -162,6 +164,12 @@ branch_io setup -D myapp.app.link,example.com,www.example.com
|
|
162
164
|
branch_io setup --no-pod-repo-update
|
163
165
|
```
|
164
166
|
|
167
|
+
##### Install using carthage bootstrap
|
168
|
+
|
169
|
+
```bash
|
170
|
+
branch_io --carthage-command "bootstrap --no-use-binaries"
|
171
|
+
```
|
172
|
+
|
165
173
|
### Validate command
|
166
174
|
|
167
175
|
```bash
|
@@ -12,7 +12,7 @@ _branch_io_complete()
|
|
12
12
|
global_opts="-h --help -t --trace -v --version"
|
13
13
|
|
14
14
|
setup_opts="$global_opts -L --live-key -T --test-key -D --domains --app-link-subdomain -U --uri-scheme"
|
15
|
-
setup_opts="$setup_opts --xcodeproj --target --frameworks --podfile --cartfile"
|
15
|
+
setup_opts="$setup_opts --xcodeproj --target --frameworks --podfile --cartfile --carthage-command"
|
16
16
|
# Don't autocomplete the default values here, e.g. --no-force, --pod-repo-update.
|
17
17
|
setup_opts="$setup_opts --no-add-sdk --no-validate --force --no-pod-repo-update --commit --no-patch-source"
|
18
18
|
|
@@ -5,7 +5,7 @@ _branch_io_complete() {
|
|
5
5
|
word="$1"
|
6
6
|
opts="-h --help -t --trace -v --version"
|
7
7
|
opts="$opts -L --live-key -T --test-key -D --domains --app-link-subdomain -U --uri-scheme"
|
8
|
-
opts="$opts --xcodeproj --target --frameworks --podfile --cartfile"
|
8
|
+
opts="$opts --xcodeproj --target --frameworks --podfile --cartfile --carthage-command"
|
9
9
|
# Don't autocomplete the default values here, e.g. --no-force, --pod-repo-update.
|
10
10
|
opts="$opts --no-add-sdk --no-validate --force --no-pod-repo-update --commit --no-patch-source"
|
11
11
|
|
data/lib/branch_io_cli/cli.rb
CHANGED
@@ -58,10 +58,10 @@ for details. To use the <%= color('setup', BOLD) %> command, you need:
|
|
58
58
|
- Domain name(s) used for Branch links
|
59
59
|
- Location of your Xcode project (may be inferred in simple projects)
|
60
60
|
|
61
|
-
|
62
|
-
|
63
|
-
|
64
|
-
|
61
|
+
If using the <%= color('--commit', BOLD) %> option, <%= color('git', BOLD) %> is required. If not using <%= color('--no-add-sdk', BOLD) %>,
|
62
|
+
the <%= color('pod', BOLD) %> or <%= color('carthage', BOLD) %> command may be required. If not found, the CLI will
|
63
|
+
offer to install and set up these command-line tools for you. Alternately, you can arrange
|
64
|
+
that the relevant commands are available in your <%= color('PATH', BOLD) %>.
|
65
65
|
|
66
66
|
All parameters are optional. A live key or test key, or both is required, as well
|
67
67
|
as at least one domain. Specify <%= color('--live-key', BOLD) %>, <%= color('--test-key', BOLD) %> or both and <%= color('--app-link-subdomain', BOLD) %>,
|
@@ -82,6 +82,7 @@ EOF
|
|
82
82
|
c.option "--target MyAppTarget", String, "Name of a target to modify in the Xcode project"
|
83
83
|
c.option "--podfile /path/to/Podfile", String, "Path to the Podfile for the project"
|
84
84
|
c.option "--cartfile /path/to/Cartfile", String, "Path to the Cartfile for the project"
|
85
|
+
c.option "--carthage-command <command>", String, "Command to run when installing from Carthage (default: update --platform ios)"
|
85
86
|
c.option "--frameworks AdSupport,CoreSpotlight,SafariServices", Array, "Comma-separated list of system frameworks to add to the project"
|
86
87
|
|
87
88
|
c.option "--[no-]pod-repo-update", "Update the local podspec repo before installing (default: yes)"
|
@@ -95,6 +96,7 @@ EOF
|
|
95
96
|
c.example "Use both live and test keys", "branch_io setup -L key_live_xxxx -T key_test_yyyy -D myapp.app.link"
|
96
97
|
c.example "Use custom or non-Branch domains", "branch_io setup -D myapp.app.link,example.com,www.example.com"
|
97
98
|
c.example "Avoid pod repo update", "branch_io setup --no-pod-repo-update"
|
99
|
+
c.example "Install using carthage bootstrap", "branch_io --carthage-command \"bootstrap --no-use-binaries\""
|
98
100
|
|
99
101
|
c.action do |args, options|
|
100
102
|
options.default(
|
@@ -104,7 +106,8 @@ EOF
|
|
104
106
|
force: false,
|
105
107
|
add_sdk: true,
|
106
108
|
patch_source: true,
|
107
|
-
commit: false
|
109
|
+
commit: false,
|
110
|
+
carthage_command: "update --platform ios"
|
108
111
|
)
|
109
112
|
Commands::SetupCommand.new(options).run!
|
110
113
|
end
|
@@ -1,3 +1,5 @@
|
|
1
|
+
require "cocoapods-core"
|
2
|
+
|
1
3
|
module BranchIOCLI
|
2
4
|
module Commands
|
3
5
|
class ReportCommand < Command
|
@@ -19,6 +21,10 @@ module BranchIOCLI
|
|
19
21
|
# TODO: Write out command-line options or configuration from helper
|
20
22
|
report.write "#{report_header}\n"
|
21
23
|
|
24
|
+
show_build_settings_cmd = "#{base_xcodebuild_cmd} -showBuildSettings"
|
25
|
+
report.write "$ #{show_build_settings_cmd}\n\n"
|
26
|
+
report.write `#{show_build_settings_cmd}`
|
27
|
+
|
22
28
|
if config_helper.clean
|
23
29
|
say "Cleaning"
|
24
30
|
clean_cmd = "#{base_xcodebuild_cmd} clean"
|
@@ -37,33 +43,111 @@ module BranchIOCLI
|
|
37
43
|
end
|
38
44
|
|
39
45
|
def base_xcodebuild_cmd
|
40
|
-
cmd = "xcodebuild"
|
46
|
+
cmd = "xcodebuild -sdk iphonesimulator"
|
41
47
|
cmd = "#{cmd} -scheme #{config_helper.scheme}" if config_helper.scheme
|
42
48
|
cmd = "#{cmd} -workspace #{config_helper.workspace_path}" if config_helper.workspace_path
|
43
|
-
cmd = "#{cmd} -project #{config_helper.xcodeproj_path}" if config_helper.xcodeproj_path
|
49
|
+
cmd = "#{cmd} -project #{config_helper.xcodeproj_path}" if config_helper.xcodeproj_path && !config_helper.workspace_path
|
44
50
|
cmd = "#{cmd} -target #{config_helper.target}" if config_helper.target
|
45
51
|
cmd = "#{cmd} -configuration #{config_helper.configuration}" if config_helper.configuration
|
46
52
|
cmd
|
47
53
|
end
|
48
54
|
|
49
55
|
def branch_version
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
59
|
-
|
56
|
+
version_from_podfile_lock ||
|
57
|
+
version_from_cartfile_resolved ||
|
58
|
+
version_from_branch_framework ||
|
59
|
+
version_from_bnc_config_m
|
60
|
+
end
|
61
|
+
|
62
|
+
def requirement_from_podfile
|
63
|
+
return nil unless config_helper.podfile_path
|
64
|
+
podfile = File.read config_helper.podfile_path
|
65
|
+
matches = /\n?\s*pod\s+("Branch"|'Branch').*?\n/m.match podfile
|
66
|
+
matches ? matches[0].strip : nil
|
67
|
+
end
|
68
|
+
|
69
|
+
def requirement_from_cartfile
|
70
|
+
return nil unless config_helper.cartfile_path
|
71
|
+
cartfile = File.read config_helper.cartfile_path
|
72
|
+
matches = %r{\n?[^\n]+?BranchMetrics/(ios-branch-deep-linking|iOS-Deferred-Deep-Linking-SDK.*?).*?\n}m.match cartfile
|
73
|
+
matches ? matches[0].strip : nil
|
74
|
+
end
|
75
|
+
|
76
|
+
def version_from_podfile_lock
|
77
|
+
return nil unless config_helper.podfile_path && File.exist?("#{config_helper.podfile_path}.lock")
|
78
|
+
podfile_lock = Pod::Lockfile.from_file Pathname.new "#{config_helper.podfile_path}.lock"
|
79
|
+
version = podfile_lock.version "Branch"
|
80
|
+
|
81
|
+
version ? "#{version} [Podfile.lock]" : nil
|
82
|
+
end
|
83
|
+
|
84
|
+
def version_from_cartfile_resolved
|
85
|
+
return nil unless config_helper.cartfile_path && File.exist?("#{config_helper.cartfile_path}.resolved")
|
86
|
+
cartfile_resolved = File.read "#{config_helper.cartfile_path}.resolved"
|
87
|
+
|
88
|
+
# Matches:
|
89
|
+
# git "https://github.com/BranchMetrics/ios-branch-deep-linking"
|
90
|
+
# git "https://github.com/BranchMetrics/ios-branch-deep-linking/"
|
91
|
+
# git "https://github.com/BranchMetrics/iOS-Deferred-Deep-Linking-SDK"
|
92
|
+
# git "https://github.com/BranchMetrics/iOS-Deferred-Deep-Linking-SDK/"
|
93
|
+
# github "BranchMetrics/ios-branch-deep-linking"
|
94
|
+
# github "BranchMetrics/ios-branch-deep-linking/"
|
95
|
+
# github "BranchMetrics/iOS-Deferred-Deep-Linking-SDK"
|
96
|
+
# github "BranchMetrics/iOS-Deferred-Deep-Linking-SDK/"
|
97
|
+
matches = %r{(ios-branch-deep-linking|iOS-Deferred-Deep-Linking-SDK)/?" "(\d+\.\d+\.\d+)"}m.match cartfile_resolved
|
98
|
+
return nil unless matches
|
99
|
+
version = matches[2]
|
100
|
+
"#{version} [Cartfile.resolved]"
|
101
|
+
end
|
102
|
+
|
103
|
+
def version_from_branch_framework
|
104
|
+
framework = config_helper.xcodeproj.frameworks_group.files.find { |f| f.path =~ /Branch.framework$/ }
|
105
|
+
return nil unless framework
|
106
|
+
framework_path = framework.real_path
|
107
|
+
info_plist_path = File.join framework_path.to_s, "Info.plist"
|
108
|
+
return nil unless File.exist? info_plist_path
|
109
|
+
|
110
|
+
require "cfpropertylist"
|
111
|
+
|
112
|
+
raw_info_plist = CFPropertyList::List.new file: info_plist_path
|
113
|
+
info_plist = CFPropertyList.native_types raw_info_plist.value
|
114
|
+
version = info_plist["CFBundleVersion"]
|
115
|
+
version ? "#{version} [Branch.framework/Info.plist]" : nil
|
116
|
+
end
|
117
|
+
|
118
|
+
def version_from_bnc_config_m
|
119
|
+
# Look for BNCConfig.m in embedded source
|
120
|
+
bnc_config_m_ref = config_helper.xcodeproj.files.find { |f| f.path =~ /BNCConfig\.m$/ }
|
121
|
+
return nil unless bnc_config_m_ref
|
122
|
+
bnc_config_m = File.read bnc_config_m_ref.real_path
|
123
|
+
matches = /BNC_SDK_VERSION\s+=\s+@"(\d+\.\d+\.\d+)"/m.match bnc_config_m
|
124
|
+
return nil unless matches
|
125
|
+
version = matches[1]
|
126
|
+
"#{version} [BNCConfig.m]"
|
60
127
|
end
|
61
128
|
|
62
129
|
def report_header
|
63
130
|
header = `xcodebuild -version`
|
131
|
+
|
132
|
+
if config_helper.podfile_path && File.exist?("#{config_helper.podfile_path}.lock")
|
133
|
+
podfile_lock = Pod::Lockfile.from_file Pathname.new "#{config_helper.podfile_path}.lock"
|
134
|
+
header = "#{header}\nUsing CocoaPods v. #{podfile_lock.cocoapods_version}\n"
|
135
|
+
end
|
136
|
+
|
137
|
+
podfile_requirement = requirement_from_podfile
|
138
|
+
header = "#{header}\nFrom Podfile:\n#{podfile_requirement}\n" if podfile_requirement
|
139
|
+
|
140
|
+
cartfile_requirement = requirement_from_cartfile
|
141
|
+
header = "#{header}\nFrom Cartfile:\n#{cartfile_requirement}\n" if cartfile_requirement
|
142
|
+
|
64
143
|
version = branch_version
|
65
|
-
|
66
|
-
|
144
|
+
if version
|
145
|
+
header = "#{header}\nBranch SDK v. #{version}\n"
|
146
|
+
else
|
147
|
+
header = "Branch SDK not found.\n"
|
148
|
+
end
|
149
|
+
|
150
|
+
header
|
67
151
|
end
|
68
152
|
end
|
69
153
|
end
|
@@ -29,11 +29,10 @@ module BranchIOCLI
|
|
29
29
|
helper.add_direct options
|
30
30
|
end
|
31
31
|
|
32
|
-
target_name = options.target # may be nil
|
33
32
|
is_app_target = !config_helper.target.extension_target_type?
|
34
33
|
|
35
34
|
if is_app_target && options.validate &&
|
36
|
-
!helper.validate_team_and_bundle_ids_from_aasa_files(
|
35
|
+
!helper.validate_team_and_bundle_ids_from_aasa_files(@domains)
|
37
36
|
say "Universal Link configuration failed validation."
|
38
37
|
helper.errors.each { |error| say " #{error}" }
|
39
38
|
return unless options.force
|
@@ -42,14 +41,14 @@ module BranchIOCLI
|
|
42
41
|
end
|
43
42
|
|
44
43
|
# the following calls can all raise IOError
|
45
|
-
helper.add_keys_to_info_plist
|
46
|
-
helper.add_branch_universal_link_domains_to_info_plist
|
44
|
+
helper.add_keys_to_info_plist @keys
|
45
|
+
helper.add_branch_universal_link_domains_to_info_plist @domains if is_app_target
|
47
46
|
helper.ensure_uri_scheme_in_info_plist if is_app_target # does nothing if already present
|
48
47
|
|
49
|
-
new_path = helper.add_universal_links_to_project
|
48
|
+
new_path = helper.add_universal_links_to_project @domains, false if is_app_target
|
50
49
|
`git add #{new_path}` if options.commit && new_path
|
51
50
|
|
52
|
-
|
51
|
+
config_helper.target.add_system_frameworks options.frameworks unless options.frameworks.nil? || options.frameworks.empty?
|
53
52
|
|
54
53
|
xcodeproj.save
|
55
54
|
|
@@ -7,17 +7,10 @@ module BranchIOCLI
|
|
7
7
|
end
|
8
8
|
|
9
9
|
def run!
|
10
|
-
# raises
|
11
|
-
xcodeproj = config_helper.xcodeproj
|
12
|
-
|
13
10
|
valid = true
|
14
11
|
|
15
12
|
unless options.domains.nil? || options.domains.empty?
|
16
|
-
domains_valid = helper.validate_project_domains(
|
17
|
-
options.domains,
|
18
|
-
xcodeproj,
|
19
|
-
options.target
|
20
|
-
)
|
13
|
+
domains_valid = helper.validate_project_domains(options.domains)
|
21
14
|
|
22
15
|
if domains_valid
|
23
16
|
say "Project domains match :domains parameter: ✅"
|
@@ -29,7 +22,7 @@ module BranchIOCLI
|
|
29
22
|
valid &&= domains_valid
|
30
23
|
end
|
31
24
|
|
32
|
-
configuration_valid = helper.validate_team_and_bundle_ids_from_aasa_files
|
25
|
+
configuration_valid = helper.validate_team_and_bundle_ids_from_aasa_files
|
33
26
|
unless configuration_valid
|
34
27
|
say "Universal Link configuration failed validation."
|
35
28
|
helper.errors.each { |error| say " #{error}" }
|
@@ -26,6 +26,7 @@ module BranchIOCLI
|
|
26
26
|
attr_reader :all_domains
|
27
27
|
attr_reader :podfile_path
|
28
28
|
attr_reader :cartfile_path
|
29
|
+
attr_reader :carthage_command
|
29
30
|
attr_reader :target
|
30
31
|
attr_reader :uri_scheme
|
31
32
|
attr_reader :pod_repo_update
|
@@ -72,9 +73,12 @@ module BranchIOCLI
|
|
72
73
|
|
73
74
|
# If --podfile is present or a Podfile was found, don't look for a Cartfile.
|
74
75
|
validate_buildfile_path options.cartfile, "Cartfile" if @sdk_integration_mode.nil? && options.add_sdk
|
76
|
+
@carthage_command = options.carthage_command if @sdk_integration_mode == :carthage
|
75
77
|
|
76
78
|
validate_sdk_addition options
|
77
79
|
|
80
|
+
BranchHelper.verify_git if @commit
|
81
|
+
|
78
82
|
print_setup_configuration
|
79
83
|
end
|
80
84
|
|
@@ -133,6 +137,7 @@ EOF
|
|
133
137
|
<%= color('URI scheme:', BOLD) %> #{@uri_scheme || '(none)'}
|
134
138
|
<%= color('Podfile:', BOLD) %> #{@podfile_path || '(none)'}
|
135
139
|
<%= color('Cartfile:', BOLD) %> #{@cartfile_path || '(none)'}
|
140
|
+
<%= color('Carthage command:', BOLD) %> #{@carthage_command || '(none)'}
|
136
141
|
<%= color('Pod repo update:', BOLD) %> #{@pod_repo_update.inspect}
|
137
142
|
<%= color('Validate:', BOLD) %> #{@validate.inspect}
|
138
143
|
<%= color('Force:', BOLD) %> #{@force.inspect}
|
@@ -263,6 +268,12 @@ EOF
|
|
263
268
|
path = options.xcodeproj
|
264
269
|
@xcodeproj = Xcodeproj::Project.open options.xcodeproj
|
265
270
|
@xcodeproj_path = options.xcodeproj
|
271
|
+
else
|
272
|
+
# Pass --workspace and --xcodeproj to override this inference.
|
273
|
+
if @workspace && @workspace.file_references.count > 0 && @workspace.file_references.first.path =~ /\.xcodeproj$/
|
274
|
+
@xcodeproj_path = File.expand_path "../#{@workspace.file_references.first.path}", @workspace_path
|
275
|
+
@xcodeproj = Xcodeproj::Project.open @xcodeproj_path
|
276
|
+
end
|
266
277
|
end
|
267
278
|
return if @workspace || @xcodeproj
|
268
279
|
rescue StandardError => e
|
@@ -271,7 +282,7 @@ EOF
|
|
271
282
|
|
272
283
|
# Try to find first a workspace, then a project
|
273
284
|
all_workspace_paths = Dir[File.expand_path(File.join(".", "**/*.xcworkspace"))]
|
274
|
-
.reject { |w| w =~ %r{/project.
|
285
|
+
.reject { |w| w =~ %r{/project.xcworkspace$} }
|
275
286
|
.select do |p|
|
276
287
|
valid = true
|
277
288
|
Pathname.new(p).each_filename do |f|
|
@@ -302,6 +313,13 @@ EOF
|
|
302
313
|
if path =~ /\.xcworkspace$/
|
303
314
|
@workspace = Xcodeproj::Workspace.new_from_xcworkspace path
|
304
315
|
@workspace_path = path
|
316
|
+
|
317
|
+
# Pass --workspace and --xcodeproj to override this inference.
|
318
|
+
if @workspace.file_references.count > 0 && @workspace.file_references.first.path =~ /\.xcodeproj$/
|
319
|
+
@xcodeproj_path = File.expand_path "../#{@workspace.file_references.first.path}", @workspace_path
|
320
|
+
@xcodeproj = Xcodeproj::Project.open @xcodeproj_path
|
321
|
+
end
|
322
|
+
|
305
323
|
return
|
306
324
|
elsif path =~ /\.xcodeproj$/
|
307
325
|
@xcodeproj = Xcodeproj::Project.open path
|
@@ -491,6 +509,7 @@ EOF
|
|
491
509
|
@podfile_path = File.expand_path "../Podfile", @xcodeproj_path
|
492
510
|
when :carthage
|
493
511
|
@cartfile_path = File.expand_path "../Cartfile", @xcodeproj_path
|
512
|
+
@carthage_command = options.carthage_command
|
494
513
|
end
|
495
514
|
end
|
496
515
|
end
|
@@ -16,25 +16,46 @@ module BranchIOCLI
|
|
16
16
|
PRODUCT_BUNDLE_IDENTIFIER = "PRODUCT_BUNDLE_IDENTIFIER"
|
17
17
|
RELEASE_CONFIGURATION = "Release"
|
18
18
|
|
19
|
-
def
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
19
|
+
def has_multiple_info_plists?
|
20
|
+
ConfigurationHelper.xcodeproj.build_configurations.inject([]) do |files, config|
|
21
|
+
files + [expanded_build_setting(ConfigurationHelper.target, "INFOPLIST_FILE", config.name)]
|
22
|
+
end.uniq.count > 1
|
23
|
+
end
|
24
|
+
|
25
|
+
def add_keys_to_info_plist(keys)
|
26
|
+
if has_multiple_info_plists?
|
27
|
+
ConfigurationHelper.xcodeproj.build_configurations.each do |config|
|
28
|
+
update_info_plist_setting config.name do |info_plist|
|
29
|
+
if keys.count > 1
|
30
|
+
# Use test key in debug configs and live key in release configs
|
31
|
+
info_plist["branch_key"] = config.debug? ? keys[:test] : keys[:live]
|
32
|
+
else
|
33
|
+
info_plist["branch_key"] = keys[:live] ? keys[:live] : keys[:test]
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
37
|
+
else
|
38
|
+
update_info_plist_setting RELEASE_CONFIGURATION do |info_plist|
|
39
|
+
# add/overwrite Branch key(s)
|
40
|
+
if keys.count > 1
|
41
|
+
info_plist["branch_key"] = keys
|
42
|
+
elsif keys[:live]
|
43
|
+
info_plist["branch_key"] = keys[:live]
|
44
|
+
else
|
45
|
+
info_plist["branch_key"] = keys[:test]
|
46
|
+
end
|
28
47
|
end
|
29
48
|
end
|
30
49
|
end
|
31
50
|
|
32
|
-
def add_branch_universal_link_domains_to_info_plist(
|
51
|
+
def add_branch_universal_link_domains_to_info_plist(domains)
|
33
52
|
# Add all supplied domains unless all are app.link domains.
|
34
53
|
return if domains.all? { |d| d =~ /app\.link$/ }
|
35
54
|
|
36
|
-
|
37
|
-
|
55
|
+
ConfigurationHelper.xcodeproj.build_configurations.each do |config|
|
56
|
+
update_info_plist_setting config.name do |info_plist|
|
57
|
+
info_plist["branch_universal_link_domains"] = domains
|
58
|
+
end
|
38
59
|
end
|
39
60
|
end
|
40
61
|
|
@@ -44,47 +65,33 @@ module BranchIOCLI
|
|
44
65
|
# No URI scheme specified. Do nothing.
|
45
66
|
return if uri_scheme.nil?
|
46
67
|
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
59
|
-
|
68
|
+
ConfigurationHelper.xcodeproj.build_configurations.each do |config|
|
69
|
+
update_info_plist_setting config.name do |info_plist|
|
70
|
+
url_types = info_plist["CFBundleURLTypes"] || []
|
71
|
+
uri_schemes = url_types.inject([]) { |schemes, t| schemes + t["CFBundleURLSchemes"] }
|
72
|
+
|
73
|
+
# Already present. Don't mess with the identifier.
|
74
|
+
next if uri_schemes.include? uri_scheme
|
75
|
+
|
76
|
+
# Not found. Add. Don't worry about the CFBundleURLName (reverse-DNS identifier)
|
77
|
+
# TODO: Should we prompt here to add or let them change the Dashboard? If there's already
|
78
|
+
# a URI scheme in the app, seems likely they'd want to use it. They may have just made
|
79
|
+
# a typo at the CLI or in the Dashboard.
|
80
|
+
url_types << {
|
81
|
+
"CFBundleURLSchemes" => [uri_scheme]
|
82
|
+
}
|
83
|
+
info_plist["CFBundleURLTypes"] = url_types
|
60
84
|
end
|
61
|
-
|
62
|
-
# Already present. Don't mess with the identifier.
|
63
|
-
return if uri_schemes.include? uri_scheme
|
64
|
-
|
65
|
-
# Not found. Add. Don't worry about the CFBundleURLName (reverse-DNS identifier)
|
66
|
-
# TODO: Should we prompt here to add or let them change the Dashboard? If there's already
|
67
|
-
# a URI scheme in the app, seems likely they'd want to use it. They may have just made
|
68
|
-
# a typo at the CLI or in the Dashboard.
|
69
|
-
url_types << {
|
70
|
-
"CFBundleURLSchemes" => [uri_scheme]
|
71
|
-
}
|
72
|
-
info_plist["CFBundleURLTypes"] = url_types
|
73
|
-
|
74
|
-
say "Added URI scheme #{uri_scheme} to project."
|
75
85
|
end
|
76
86
|
end
|
77
87
|
|
78
|
-
def update_info_plist_setting(
|
79
|
-
# raises
|
80
|
-
target = target_from_project project, target_name
|
81
|
-
|
88
|
+
def update_info_plist_setting(configuration = RELEASE_CONFIGURATION, &b)
|
82
89
|
# find the Info.plist paths for this configuration
|
83
|
-
info_plist_path = expanded_build_setting target, "INFOPLIST_FILE", configuration
|
90
|
+
info_plist_path = expanded_build_setting ConfigurationHelper.target, "INFOPLIST_FILE", configuration
|
84
91
|
|
85
92
|
raise "Info.plist not found for configuration #{configuration}" if info_plist_path.nil?
|
86
93
|
|
87
|
-
project_parent = File.dirname
|
94
|
+
project_parent = File.dirname ConfigurationHelper.xcodeproj_path
|
88
95
|
|
89
96
|
info_plist_path = File.expand_path info_plist_path, project_parent
|
90
97
|
|
@@ -98,9 +105,9 @@ module BranchIOCLI
|
|
98
105
|
add_change info_plist_path
|
99
106
|
end
|
100
107
|
|
101
|
-
def add_universal_links_to_project(
|
102
|
-
|
103
|
-
target =
|
108
|
+
def add_universal_links_to_project(domains, remove_existing, configuration = RELEASE_CONFIGURATION)
|
109
|
+
project = ConfigurationHelper.xcodeproj
|
110
|
+
target = ConfigurationHelper.target
|
104
111
|
|
105
112
|
relative_entitlements_path = expanded_build_setting target, CODE_SIGN_ENTITLEMENTS, configuration
|
106
113
|
project_parent = File.dirname project.path
|
@@ -150,7 +157,7 @@ module BranchIOCLI
|
|
150
157
|
[team, bundle]
|
151
158
|
end
|
152
159
|
|
153
|
-
def update_team_and_bundle_ids_from_aasa_file(
|
160
|
+
def update_team_and_bundle_ids_from_aasa_file(domain)
|
154
161
|
# raises
|
155
162
|
identifiers = app_ids_from_aasa_file domain
|
156
163
|
raise "Multiple appIDs found in AASA file" if identifiers.count > 1
|
@@ -158,11 +165,11 @@ module BranchIOCLI
|
|
158
165
|
identifier = identifiers[0]
|
159
166
|
team, bundle = team_and_bundle_from_app_id identifier
|
160
167
|
|
161
|
-
update_team_and_bundle_ids
|
162
|
-
add_change
|
168
|
+
update_team_and_bundle_ids team, bundle
|
169
|
+
add_change ConfigurationHelper.xcodeproj_path
|
163
170
|
end
|
164
171
|
|
165
|
-
def validate_team_and_bundle_ids_from_aasa_files(
|
172
|
+
def validate_team_and_bundle_ids_from_aasa_files(domains = [], remove_existing = false, configuration = RELEASE_CONFIGURATION)
|
166
173
|
@errors = []
|
167
174
|
valid = true
|
168
175
|
|
@@ -172,7 +179,7 @@ module BranchIOCLI
|
|
172
179
|
# Don't validate domains to be removed (#16)
|
173
180
|
all_domains = domains
|
174
181
|
else
|
175
|
-
all_domains = (domains + domains_from_project(
|
182
|
+
all_domains = (domains + domains_from_project(configuration)).uniq
|
176
183
|
end
|
177
184
|
|
178
185
|
if all_domains.empty?
|
@@ -184,7 +191,7 @@ module BranchIOCLI
|
|
184
191
|
end
|
185
192
|
|
186
193
|
all_domains.each do |domain|
|
187
|
-
domain_valid = validate_team_and_bundle_ids
|
194
|
+
domain_valid = validate_team_and_bundle_ids domain, configuration
|
188
195
|
valid &&= domain_valid
|
189
196
|
say "Valid Universal Link configuration for #{domain} ✅" if domain_valid
|
190
197
|
end
|
@@ -272,9 +279,8 @@ module BranchIOCLI
|
|
272
279
|
nil
|
273
280
|
end
|
274
281
|
|
275
|
-
def validate_team_and_bundle_ids(
|
276
|
-
|
277
|
-
target = target_from_project project, target_name
|
282
|
+
def validate_team_and_bundle_ids(domain, configuration)
|
283
|
+
target = ConfigurationHelper.target
|
278
284
|
|
279
285
|
product_bundle_identifier = expanded_build_setting target, PRODUCT_BUNDLE_IDENTIFIER, configuration
|
280
286
|
development_team = expanded_build_setting target, DEVELOPMENT_TEAM, configuration
|
@@ -292,9 +298,9 @@ module BranchIOCLI
|
|
292
298
|
match_found
|
293
299
|
end
|
294
300
|
|
295
|
-
def validate_project_domains(expected,
|
301
|
+
def validate_project_domains(expected, configuration = RELEASE_CONFIGURATION)
|
296
302
|
@errors = []
|
297
|
-
project_domains = domains_from_project
|
303
|
+
project_domains = domains_from_project configuration
|
298
304
|
valid = expected.count == project_domains.count
|
299
305
|
if valid
|
300
306
|
sorted = expected.sort
|
@@ -312,9 +318,8 @@ module BranchIOCLI
|
|
312
318
|
valid
|
313
319
|
end
|
314
320
|
|
315
|
-
def update_team_and_bundle_ids(
|
316
|
-
|
317
|
-
target = target_from_project project, target_name
|
321
|
+
def update_team_and_bundle_ids(team, bundle)
|
322
|
+
target = ConfigurationHelper.target
|
318
323
|
|
319
324
|
target.build_configuration_list.set_setting PRODUCT_BUNDLE_IDENTIFIER, bundle
|
320
325
|
target.build_configuration_list.set_setting DEVELOPMENT_TEAM, team
|
@@ -338,9 +343,9 @@ module BranchIOCLI
|
|
338
343
|
target
|
339
344
|
end
|
340
345
|
|
341
|
-
def domains_from_project(
|
342
|
-
|
343
|
-
target =
|
346
|
+
def domains_from_project(configuration = RELEASE_CONFIGURATION)
|
347
|
+
project = ConfigurationHelper.xcodeproj
|
348
|
+
target = ConfigurationHelper.target
|
344
349
|
|
345
350
|
relative_entitlements_path = expanded_build_setting target, CODE_SIGN_ENTITLEMENTS, configuration
|
346
351
|
return [] if relative_entitlements_path.nil?
|
@@ -373,12 +378,6 @@ module BranchIOCLI
|
|
373
378
|
setting_value
|
374
379
|
end
|
375
380
|
|
376
|
-
def add_system_frameworks(project, target_name, frameworks)
|
377
|
-
target = target_from_project project, target_name
|
378
|
-
|
379
|
-
target.add_system_framework frameworks
|
380
|
-
end
|
381
|
-
|
382
381
|
def patch_app_delegate_swift(project)
|
383
382
|
app_delegate_swift = project.files.find { |f| f.path =~ /AppDelegate.swift$/ }
|
384
383
|
return false if app_delegate_swift.nil?
|
@@ -397,14 +396,53 @@ module BranchIOCLI
|
|
397
396
|
mode: :prepend
|
398
397
|
)
|
399
398
|
|
400
|
-
|
399
|
+
patch_did_finish_launching_method_swift app_delegate_swift_path
|
400
|
+
patch_continue_user_activity_method_swift app_delegate_swift_path
|
401
|
+
patch_open_url_method_swift app_delegate_swift_path
|
402
|
+
|
403
|
+
add_change app_delegate_swift_path
|
404
|
+
true
|
405
|
+
end
|
406
|
+
|
407
|
+
def patch_app_delegate_objc(project)
|
408
|
+
app_delegate_objc = project.files.find { |f| f.path =~ /AppDelegate.m$/ }
|
409
|
+
return false if app_delegate_objc.nil?
|
410
|
+
|
411
|
+
app_delegate_objc_path = app_delegate_objc.real_path.to_s
|
412
|
+
|
413
|
+
app_delegate = File.read app_delegate_objc_path
|
414
|
+
return false if app_delegate =~ %r{^\s+#import\s+<Branch/Branch.h>|^\s+@import\s+Branch;}
|
415
|
+
|
416
|
+
say "Patching #{app_delegate_objc_path}"
|
417
|
+
|
418
|
+
apply_patch(
|
419
|
+
files: app_delegate_objc_path,
|
420
|
+
regexp: /^\s+@import|^\s+#import.*$/,
|
421
|
+
text: "\n#import <Branch/Branch.h>",
|
422
|
+
mode: :prepend
|
423
|
+
)
|
424
|
+
|
425
|
+
patch_did_finish_launching_method_objc app_delegate_objc_path
|
426
|
+
patch_continue_user_activity_method_objc app_delegate_objc_path
|
427
|
+
patch_open_url_method_objc app_delegate_objc_path
|
428
|
+
|
429
|
+
add_change app_delegate_objc_path
|
430
|
+
true
|
431
|
+
end
|
432
|
+
|
433
|
+
def patch_did_finish_launching_method_swift(app_delegate_swift_path)
|
434
|
+
app_delegate_swift = File.read app_delegate_swift_path
|
435
|
+
|
436
|
+
if app_delegate_swift =~ /didFinishLaunching[^\n]+?\{/m
|
437
|
+
# method already present
|
438
|
+
init_session_text = ConfigurationHelper.keys.count <= 1 || has_multiple_info_plists? ? "" : <<EOF
|
401
439
|
#if DEBUG
|
402
440
|
Branch.setUseTestBranchKey(true)
|
403
441
|
#endif
|
404
442
|
|
405
443
|
EOF
|
406
444
|
|
407
|
-
|
445
|
+
init_session_text += <<-EOF
|
408
446
|
Branch.getInstance().initSession(launchOptions: launchOptions) {
|
409
447
|
universalObject, linkProperties, error in
|
410
448
|
|
@@ -412,130 +450,105 @@ EOF
|
|
412
450
|
}
|
413
451
|
EOF
|
414
452
|
|
415
|
-
apply_patch(
|
416
|
-
files: app_delegate_swift_path,
|
417
|
-
regexp: /didFinishLaunchingWithOptions.*?\{[^\n]*\n/m,
|
418
|
-
text: init_session_text,
|
419
|
-
mode: :append
|
420
|
-
)
|
421
|
-
|
422
|
-
if app_delegate =~ /application:.*continue userActivity:.*restorationHandler:/
|
423
|
-
# Add something to the top of the method
|
424
|
-
continue_user_activity_text = <<-EOF
|
425
|
-
// TODO: Adjust your method as you see fit.
|
426
|
-
if Branch.getInstance.continue(userActivity) {
|
427
|
-
return true
|
428
|
-
}
|
429
|
-
|
430
|
-
EOF
|
431
|
-
|
432
453
|
apply_patch(
|
433
454
|
files: app_delegate_swift_path,
|
434
|
-
regexp: /
|
435
|
-
text:
|
455
|
+
regexp: /didFinishLaunchingWithOptions.*?\{[^\n]*\n/m,
|
456
|
+
text: init_session_text,
|
436
457
|
mode: :append
|
437
458
|
)
|
438
459
|
else
|
439
|
-
#
|
440
|
-
continue_user_activity_text = <<-EOF
|
460
|
+
# method not present. add entire method
|
441
461
|
|
462
|
+
method_text = <<EOF
|
442
463
|
|
443
|
-
func application(_ application: UIApplication,
|
444
|
-
|
464
|
+
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {
|
465
|
+
EOF
|
466
|
+
|
467
|
+
if ConfigurationHelper.keys.count > 1 && !has_multiple_info_plists?
|
468
|
+
method_text += <<EOF
|
469
|
+
#if DEBUG
|
470
|
+
Branch.setUseTestBranchKey(true)
|
471
|
+
#endif
|
472
|
+
|
473
|
+
EOF
|
474
|
+
end
|
475
|
+
|
476
|
+
method_text += <<-EOF
|
477
|
+
Branch.getInstance().initSession(launchOptions: launchOptions) {
|
478
|
+
universalObject, linkProperties, error in
|
479
|
+
|
480
|
+
// TODO: Route Branch links
|
481
|
+
}
|
482
|
+
return true
|
445
483
|
}
|
446
|
-
|
484
|
+
EOF
|
447
485
|
|
448
486
|
apply_patch(
|
449
487
|
files: app_delegate_swift_path,
|
450
|
-
regexp:
|
451
|
-
text:
|
452
|
-
mode: :
|
488
|
+
regexp: /var\s+window\s?:\s?UIWindow\?.*?\n/m,
|
489
|
+
text: method_text,
|
490
|
+
mode: :append
|
453
491
|
)
|
454
492
|
end
|
455
|
-
|
456
|
-
patch_open_url_method_swift app_delegate_swift_path
|
457
|
-
|
458
|
-
add_change app_delegate_swift_path
|
459
|
-
true
|
460
493
|
end
|
461
494
|
|
462
|
-
def
|
463
|
-
app_delegate_objc =
|
464
|
-
return false if app_delegate_objc.nil?
|
465
|
-
|
466
|
-
app_delegate_objc_path = app_delegate_objc.real_path.to_s
|
467
|
-
|
468
|
-
app_delegate = File.read app_delegate_objc_path
|
469
|
-
return false if app_delegate =~ %r{^\s+#import\s+<Branch/Branch.h>|^\s+@import\s+Branch;}
|
470
|
-
|
471
|
-
say "Patching #{app_delegate_objc_path}"
|
472
|
-
|
473
|
-
apply_patch(
|
474
|
-
files: app_delegate_objc_path,
|
475
|
-
regexp: /^\s+@import|^\s+#import.*$/,
|
476
|
-
text: "\n#import <Branch/Branch.h>",
|
477
|
-
mode: :prepend
|
478
|
-
)
|
495
|
+
def patch_did_finish_launching_method_objc(app_delegate_objc_path)
|
496
|
+
app_delegate_objc = File.read app_delegate_objc_path
|
479
497
|
|
480
|
-
|
498
|
+
if app_delegate_objc =~ /didFinishLaunchingWithOptions/m
|
499
|
+
# method exists. patch it.
|
500
|
+
init_session_text = ConfigurationHelper.keys.count <= 1 || has_multiple_info_plists? ? "" : <<EOF
|
481
501
|
#ifdef DEBUG
|
482
502
|
[Branch setUseTestBranchKey:YES];
|
483
503
|
#endif // DEBUG
|
484
504
|
|
485
505
|
EOF
|
486
506
|
|
487
|
-
|
507
|
+
init_session_text += <<-EOF
|
488
508
|
[[Branch getInstance] initSessionWithLaunchOptions:launchOptions
|
489
509
|
andRegisterDeepLinkHandlerUsingBranchUniversalObject:^(BranchUniversalObject *universalObject, BranchLinkProperties *linkProperties, NSError *error){
|
490
510
|
// TODO: Route Branch links
|
491
511
|
}];
|
492
|
-
|
493
|
-
|
494
|
-
apply_patch(
|
495
|
-
files: app_delegate_objc_path,
|
496
|
-
regexp: /didFinishLaunchingWithOptions.*?\{[^\n]*\n/m,
|
497
|
-
text: init_session_text,
|
498
|
-
mode: :append
|
499
|
-
)
|
500
|
-
|
501
|
-
if app_delegate =~ /application:.*continueUserActivity:.*restorationHandler:/
|
502
|
-
continue_user_activity_text = <<-EOF
|
503
|
-
// TODO: Adjust your method as you see fit.
|
504
|
-
if ([[Branch getInstance] continueUserActivity:userActivity]) {
|
505
|
-
return YES;
|
506
|
-
}
|
507
|
-
|
508
|
-
EOF
|
512
|
+
EOF
|
509
513
|
|
510
514
|
apply_patch(
|
511
515
|
files: app_delegate_objc_path,
|
512
|
-
regexp: /
|
513
|
-
text:
|
516
|
+
regexp: /didFinishLaunchingWithOptions.*?\{[^\n]*\n/m,
|
517
|
+
text: init_session_text,
|
514
518
|
mode: :append
|
515
519
|
)
|
516
520
|
else
|
517
|
-
#
|
518
|
-
|
521
|
+
# method does not exist. add it.
|
522
|
+
method_text = <<EOF
|
519
523
|
|
524
|
+
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
|
525
|
+
EOF
|
520
526
|
|
521
|
-
|
522
|
-
|
523
|
-
|
527
|
+
if ConfigurationHelper.keys.count > 1 && !has_multiple_info_plists?
|
528
|
+
method_text += <<EOF
|
529
|
+
#ifdef DEBUG
|
530
|
+
[Branch setUseTestBranchKey:YES];
|
531
|
+
#endif // DEBUG
|
532
|
+
|
533
|
+
EOF
|
534
|
+
end
|
535
|
+
|
536
|
+
method_text += <<-EOF
|
537
|
+
[[Branch getInstance] initSessionWithLaunchOptions:launchOptions
|
538
|
+
andRegisterDeepLinkHandlerUsingBranchUniversalObject:^(BranchUniversalObject *universalObject, BranchLinkProperties *linkProperties, NSError *error){
|
539
|
+
// TODO: Route Branch links
|
540
|
+
}];
|
541
|
+
return YES;
|
524
542
|
}
|
525
543
|
EOF
|
526
544
|
|
527
545
|
apply_patch(
|
528
546
|
files: app_delegate_objc_path,
|
529
|
-
regexp:
|
530
|
-
text:
|
531
|
-
mode: :
|
547
|
+
regexp: /^@implementation.*?\n/m,
|
548
|
+
text: method_text,
|
549
|
+
mode: :append
|
532
550
|
)
|
533
551
|
end
|
534
|
-
|
535
|
-
patch_open_url_method_objc app_delegate_objc_path
|
536
|
-
|
537
|
-
add_change app_delegate_objc_path
|
538
|
-
true
|
539
552
|
end
|
540
553
|
|
541
554
|
def patch_open_url_method_swift(app_delegate_swift_path)
|
@@ -592,6 +605,43 @@ EOF
|
|
592
605
|
end
|
593
606
|
end
|
594
607
|
|
608
|
+
def patch_continue_user_activity_method_swift(app_delegate_swift_path)
|
609
|
+
app_delegate = File.read app_delegate_swift_path
|
610
|
+
if app_delegate =~ /application:.*continue userActivity:.*restorationHandler:/
|
611
|
+
# Add something to the top of the method
|
612
|
+
continue_user_activity_text = <<-EOF
|
613
|
+
// TODO: Adjust your method as you see fit.
|
614
|
+
if Branch.getInstance.continue(userActivity) {
|
615
|
+
return true
|
616
|
+
}
|
617
|
+
|
618
|
+
EOF
|
619
|
+
|
620
|
+
apply_patch(
|
621
|
+
files: app_delegate_swift_path,
|
622
|
+
regexp: /application:.*continue userActivity:.*restorationHandler:.*?\{.*?\n/m,
|
623
|
+
text: continue_user_activity_text,
|
624
|
+
mode: :append
|
625
|
+
)
|
626
|
+
else
|
627
|
+
# Add the application:continueUserActivity:restorationHandler method if it does not exist
|
628
|
+
continue_user_activity_text = <<-EOF
|
629
|
+
|
630
|
+
|
631
|
+
func application(_ application: UIApplication, continue userActivity: NSUserActivity, restorationHandler: @escaping ([Any]?) -> Void) -> Bool {
|
632
|
+
return Branch.getInstance().continue(userActivity)
|
633
|
+
}
|
634
|
+
EOF
|
635
|
+
|
636
|
+
apply_patch(
|
637
|
+
files: app_delegate_swift_path,
|
638
|
+
regexp: /\n\s*\}[^{}]*\Z/m,
|
639
|
+
text: continue_user_activity_text,
|
640
|
+
mode: :prepend
|
641
|
+
)
|
642
|
+
end
|
643
|
+
end
|
644
|
+
|
595
645
|
def patch_open_url_method_objc(app_delegate_objc_path)
|
596
646
|
app_delegate_objc = File.read app_delegate_objc_path
|
597
647
|
if app_delegate_objc =~ /application:.*openURL:.*options/
|
@@ -646,21 +696,69 @@ EOF
|
|
646
696
|
end
|
647
697
|
end
|
648
698
|
|
699
|
+
def patch_continue_user_activity_method_objc(app_delegate_objc_path)
|
700
|
+
app_delegate = File.read app_delegate_objc_path
|
701
|
+
if app_delegate =~ /application:.*continueUserActivity:.*restorationHandler:/
|
702
|
+
continue_user_activity_text = <<-EOF
|
703
|
+
// TODO: Adjust your method as you see fit.
|
704
|
+
if ([[Branch getInstance] continueUserActivity:userActivity]) {
|
705
|
+
return YES;
|
706
|
+
}
|
707
|
+
|
708
|
+
EOF
|
709
|
+
|
710
|
+
apply_patch(
|
711
|
+
files: app_delegate_objc_path,
|
712
|
+
regexp: /application:.*continueUserActivity:.*restorationHandler:.*?\{.*?\n/m,
|
713
|
+
text: continue_user_activity_text,
|
714
|
+
mode: :append
|
715
|
+
)
|
716
|
+
else
|
717
|
+
# Add the application:continueUserActivity:restorationHandler method if it does not exist
|
718
|
+
continue_user_activity_text = <<-EOF
|
719
|
+
|
720
|
+
|
721
|
+
- (BOOL)application:(UIApplication *)app continueUserActivity:(nonnull NSUserActivity *)userActivity restorationHandler:(nonnull void (^)(NSArray * _Nullable))restorationHandler
|
722
|
+
{
|
723
|
+
return [[Branch getInstance] continueUserActivity:userActivity];
|
724
|
+
}
|
725
|
+
EOF
|
726
|
+
|
727
|
+
apply_patch(
|
728
|
+
files: app_delegate_objc_path,
|
729
|
+
regexp: /\n\s*@end[^@]*\Z/m,
|
730
|
+
text: continue_user_activity_text,
|
731
|
+
mode: :prepend
|
732
|
+
)
|
733
|
+
end
|
734
|
+
end
|
735
|
+
|
649
736
|
def patch_podfile(podfile_path)
|
650
737
|
podfile = File.read podfile_path
|
651
738
|
|
652
739
|
# Podfile already contains the Branch pod
|
740
|
+
# TODO: Allow for adding to multiple targets in the Podfile
|
653
741
|
return false if podfile =~ /pod\s+('Branch'|"Branch")/
|
654
742
|
|
655
743
|
say "Adding pod \"Branch\" to #{podfile_path}"
|
656
744
|
|
657
|
-
|
658
|
-
|
659
|
-
|
660
|
-
|
661
|
-
|
662
|
-
|
663
|
-
|
745
|
+
if podfile =~ /target\s+(["'])#{ConfigurationHelper.target.name}\1\s+do.*?\n/m
|
746
|
+
# if there is a target block for this target:
|
747
|
+
apply_patch(
|
748
|
+
files: podfile_path,
|
749
|
+
regexp: /\n(\s*)target\s+(["'])#{ConfigurationHelper.target.name}\2\s+do.*?\n/m,
|
750
|
+
text: "\\1 pod \"Branch\"\n",
|
751
|
+
mode: :append
|
752
|
+
)
|
753
|
+
else
|
754
|
+
# add to the abstract_target for this target
|
755
|
+
apply_patch(
|
756
|
+
files: podfile_path,
|
757
|
+
regexp: /^(\s*)target\s+["']#{ConfigurationHelper.target.name}/,
|
758
|
+
text: "\\1pod \"Branch\"\n",
|
759
|
+
mode: :prepend
|
760
|
+
)
|
761
|
+
end
|
664
762
|
|
665
763
|
true
|
666
764
|
end
|
@@ -684,12 +782,14 @@ EOF
|
|
684
782
|
end
|
685
783
|
|
686
784
|
def add_cocoapods(options)
|
785
|
+
verify_cocoapods
|
786
|
+
|
687
787
|
podfile_path = ConfigurationHelper.podfile_path
|
688
788
|
|
689
789
|
install_command = "pod install"
|
690
790
|
install_command += " --repo-update" if options.pod_repo_update
|
691
791
|
Dir.chdir(File.dirname(podfile_path)) do
|
692
|
-
|
792
|
+
system_command "pod init"
|
693
793
|
apply_patch(
|
694
794
|
files: podfile_path,
|
695
795
|
regexp: /^(\s*)# Pods for #{ConfigurationHelper.target.name}$/,
|
@@ -697,7 +797,7 @@ EOF
|
|
697
797
|
text: "\n\\1pod \"Branch\"",
|
698
798
|
global: false
|
699
799
|
)
|
700
|
-
|
800
|
+
system_command install_command
|
701
801
|
end
|
702
802
|
|
703
803
|
add_change podfile_path
|
@@ -714,6 +814,7 @@ EOF
|
|
714
814
|
|
715
815
|
def add_carthage(options)
|
716
816
|
# TODO: Collapse this and Command::update_cartfile
|
817
|
+
verify_carthage
|
717
818
|
|
718
819
|
# 1. Generate Cartfile
|
719
820
|
cartfile_path = ConfigurationHelper.cartfile_path
|
@@ -725,7 +826,7 @@ EOF
|
|
725
826
|
|
726
827
|
# 2. carthage update
|
727
828
|
Dir.chdir(File.dirname(cartfile_path)) do
|
728
|
-
|
829
|
+
system_command "carthage #{ConfigurationHelper.carthage_command}"
|
729
830
|
end
|
730
831
|
|
731
832
|
# 3. Add Cartfile and Cartfile.resolved to commit (in case :commit param specified)
|
@@ -797,7 +898,7 @@ EOF
|
|
797
898
|
|
798
899
|
# Now the current framework is in framework_path
|
799
900
|
|
800
|
-
say "Adding to #{
|
901
|
+
say "Adding to #{ConfigurationHelper.xcodeproj_path}"
|
801
902
|
|
802
903
|
# Add as a dependency in the Frameworks group
|
803
904
|
framework = frameworks_group.new_file "Branch.framework" # relative to frameworks_group.real_path
|
@@ -824,6 +925,8 @@ EOF
|
|
824
925
|
end
|
825
926
|
|
826
927
|
def update_podfile(options)
|
928
|
+
verify_cocoapods
|
929
|
+
|
827
930
|
podfile_path = ConfigurationHelper.podfile_path
|
828
931
|
return false if podfile_path.nil?
|
829
932
|
|
@@ -836,7 +939,7 @@ EOF
|
|
836
939
|
command += ' --repo-update' if options.pod_repo_update
|
837
940
|
|
838
941
|
Dir.chdir(File.dirname(podfile_path)) do
|
839
|
-
|
942
|
+
system_command command
|
840
943
|
end
|
841
944
|
|
842
945
|
# 3. Add Podfile and Podfile.lock to commit (in case :commit param specified)
|
@@ -856,6 +959,8 @@ EOF
|
|
856
959
|
end
|
857
960
|
|
858
961
|
def update_cartfile(options, project)
|
962
|
+
verify_carthage
|
963
|
+
|
859
964
|
cartfile_path = ConfigurationHelper.cartfile_path
|
860
965
|
return false if cartfile_path.nil?
|
861
966
|
|
@@ -864,7 +969,7 @@ EOF
|
|
864
969
|
|
865
970
|
# 2. carthage update
|
866
971
|
Dir.chdir(File.dirname(cartfile_path)) do
|
867
|
-
|
972
|
+
system_command "carthage #{ConfigurationHelper.carthage_command}"
|
868
973
|
end
|
869
974
|
|
870
975
|
# 3. Add Cartfile and Cartfile.resolved to commit (in case :commit param specified)
|
@@ -903,6 +1008,79 @@ EOF
|
|
903
1008
|
def patch_source(xcodeproj)
|
904
1009
|
patch_app_delegate_swift(xcodeproj) || patch_app_delegate_objc(xcodeproj)
|
905
1010
|
end
|
1011
|
+
|
1012
|
+
def verify_cocoapods
|
1013
|
+
pod_cmd = `which pod`
|
1014
|
+
return unless pod_cmd.empty?
|
1015
|
+
|
1016
|
+
gem_cmd = `which gem`
|
1017
|
+
if gem_cmd.empty?
|
1018
|
+
say "'pod' command not available in PATH and 'gem' command not available in PATH to install cocoapods."
|
1019
|
+
exit(-1)
|
1020
|
+
end
|
1021
|
+
|
1022
|
+
install = ask "'pod' command not available in PATH. Install cocoapods (may require a sudo password) (Y/n)? "
|
1023
|
+
if install.downcase =~ /^n/
|
1024
|
+
say "Please install cocoapods or use --no-add-sdk to continue."
|
1025
|
+
exit(-1)
|
1026
|
+
end
|
1027
|
+
|
1028
|
+
gem_home = ENV["GEM_HOME"]
|
1029
|
+
if gem_home && File.writable?(gem_home)
|
1030
|
+
system_command "gem install cocoapods"
|
1031
|
+
else
|
1032
|
+
system_command "sudo gem install cocoapods"
|
1033
|
+
end
|
1034
|
+
|
1035
|
+
# Ensure master podspec repo is set up (will update if it exists).
|
1036
|
+
system_command "pod setup"
|
1037
|
+
end
|
1038
|
+
|
1039
|
+
def verify_carthage
|
1040
|
+
carthage_cmd = `which carthage`
|
1041
|
+
return unless carthage_cmd.empty?
|
1042
|
+
|
1043
|
+
brew_cmd = `which brew`
|
1044
|
+
if brew_cmd.empty?
|
1045
|
+
say "'carthage' command not available in PATH and 'brew' command not available in PATH to install 'carthage'."
|
1046
|
+
exit(-1)
|
1047
|
+
end
|
1048
|
+
|
1049
|
+
install = ask "'carthage' command not available in PATH. Use Homebrew to install carthage (Y/n)? "
|
1050
|
+
if install.downcase =~ /^n/
|
1051
|
+
say "Please install carthage or use --no-add-sdk to continue."
|
1052
|
+
exit(-1)
|
1053
|
+
end
|
1054
|
+
|
1055
|
+
system_command "brew install carthage"
|
1056
|
+
end
|
1057
|
+
|
1058
|
+
def verify_git
|
1059
|
+
return unless ConfigurationHelper.commit
|
1060
|
+
|
1061
|
+
git_cmd = `which git`
|
1062
|
+
return unless git_cmd.empty?
|
1063
|
+
|
1064
|
+
xcode_select_path = `which xcode-select`
|
1065
|
+
if xcode_select_path.empty?
|
1066
|
+
say "'git' command not available in PATH and 'xcode-select' command not available in PATH to install 'git'."
|
1067
|
+
exit(-1)
|
1068
|
+
end
|
1069
|
+
|
1070
|
+
install = ask "'git' command not available in PATH. Install Xcode command-line tools (requires password) (Y/n)? "
|
1071
|
+
if install.downcase =~ /^n/
|
1072
|
+
say "Please install Xcode command tools or leave out the --commit option to continue."
|
1073
|
+
exit(-1)
|
1074
|
+
end
|
1075
|
+
|
1076
|
+
system_command "xcode-select --install"
|
1077
|
+
end
|
1078
|
+
|
1079
|
+
def system_command(command)
|
1080
|
+
# TODO: Not working well with bundle exec atm.
|
1081
|
+
say "<%= color(\"$ #{command}\", BOLD) %>"
|
1082
|
+
system command
|
1083
|
+
end
|
906
1084
|
end
|
907
1085
|
end
|
908
1086
|
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: branch_io_cli
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.7.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Branch
|
@@ -9,8 +9,36 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2017-
|
12
|
+
date: 2017-11-01 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
|
+
- !ruby/object:Gem::Dependency
|
15
|
+
name: CFPropertyList
|
16
|
+
requirement: !ruby/object:Gem::Requirement
|
17
|
+
requirements:
|
18
|
+
- - ">="
|
19
|
+
- !ruby/object:Gem::Version
|
20
|
+
version: '0'
|
21
|
+
type: :runtime
|
22
|
+
prerelease: false
|
23
|
+
version_requirements: !ruby/object:Gem::Requirement
|
24
|
+
requirements:
|
25
|
+
- - ">="
|
26
|
+
- !ruby/object:Gem::Version
|
27
|
+
version: '0'
|
28
|
+
- !ruby/object:Gem::Dependency
|
29
|
+
name: cocoapods-core
|
30
|
+
requirement: !ruby/object:Gem::Requirement
|
31
|
+
requirements:
|
32
|
+
- - ">="
|
33
|
+
- !ruby/object:Gem::Version
|
34
|
+
version: '0'
|
35
|
+
type: :runtime
|
36
|
+
prerelease: false
|
37
|
+
version_requirements: !ruby/object:Gem::Requirement
|
38
|
+
requirements:
|
39
|
+
- - ">="
|
40
|
+
- !ruby/object:Gem::Version
|
41
|
+
version: '0'
|
14
42
|
- !ruby/object:Gem::Dependency
|
15
43
|
name: commander
|
16
44
|
requirement: !ruby/object:Gem::Requirement
|