update_repo 0.6.3 → 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/.gitignore +1 -0
- data/README.md +4 -4
- data/Rakefile +1 -1
- data/lib/update_repo/helpers.rb +18 -10
- data/lib/update_repo/version.rb +1 -1
- data/lib/update_repo.rb +69 -45
- data/update_repo.gemspec +1 -0
- metadata +16 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 00f7cdd0ea4d8be3e8cde3ce7af7d2bea7edfa18
|
4
|
+
data.tar.gz: b4d2f9eba172fa64293855bb3acb03e09b16024e
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 4442b8cf9ffc01891eef1828f5fcf4c88f417cfcb7a7ec2268d0d9b1e19c7b0b0ddd7e922ea3b99de9b47c1065cf871300e08ae7f84274bd553d592af91e0bd4
|
7
|
+
data.tar.gz: 25439ccabe091bcc00b4c968272c3b00043aa3ffcf4a285b740877d47423ca9d9830dd26160d84631ff109fcbbcfab618b1c82eeabaf710d166d205d0125a98a
|
data/.gitignore
CHANGED
data/README.md
CHANGED
@@ -78,8 +78,7 @@ Not in any specific order :
|
|
78
78
|
- Error checking and reporting for the git processes `[IN PROGRESS]`
|
79
79
|
* Add more failure cases, not all git errors fail with "fatal:"
|
80
80
|
- retry for connection issues etc (config setting).
|
81
|
-
-
|
82
|
-
* list of changed repos
|
81
|
+
- Improve the stats / info at end-of-job :
|
83
82
|
* errors or connection problems `[IN PROGRESS]`
|
84
83
|
* _more..._
|
85
84
|
- Add command line options to override configuration, and even specify an alternate config file. Any options so specified will have precedence over settings specified in the configuration file.
|
@@ -87,9 +86,10 @@ Not in any specific order :
|
|
87
86
|
- Add ability to specify a new directory (containing Git repos) to search from the command line, and optionally save this to the standard configuration.
|
88
87
|
- Add new repo from the command line that will be cloned to the default repo directory and then updated as usual. Extra flag added for "add only, clone later" for offline use.
|
89
88
|
- Add flag for 'default' repo directory (or another specific directory - if it does not already exist it will be created and added to the standard list) which will be used for new additions.
|
90
|
-
- Option to save log file for each run.
|
91
89
|
- Add option to only display a (text) tree of the discovered git repositories, not updating them; Similar option to just dump a list of the remote git locations.
|
92
|
-
- Add
|
90
|
+
- Add Import & Export functionality :
|
91
|
+
* ability to export a text dump of each repo location `[DONE]`
|
92
|
+
* re-import the above dump on a different machine or after reinstall
|
93
93
|
- Document configuration file format and options.
|
94
94
|
- Add testing!
|
95
95
|
|
data/Rakefile
CHANGED
data/lib/update_repo/helpers.rb
CHANGED
@@ -14,9 +14,6 @@ module Helpers
|
|
14
14
|
File.join(path_array)
|
15
15
|
end
|
16
16
|
|
17
|
-
# mark these as private simply so that 'reek' wont flag as utility function.
|
18
|
-
private
|
19
|
-
|
20
17
|
# true if we are dumping the file structure and git urls instead of updating.
|
21
18
|
def dumping?
|
22
19
|
param_set('dump')
|
@@ -27,6 +24,23 @@ module Helpers
|
|
27
24
|
param_set('import')
|
28
25
|
end
|
29
26
|
|
27
|
+
# true if we are logging to file.
|
28
|
+
def logging?
|
29
|
+
param_set('log')
|
30
|
+
end
|
31
|
+
|
32
|
+
# this function will simply pass the given string to 'print', and also
|
33
|
+
# log to file if that is specified.
|
34
|
+
def print_log(*string)
|
35
|
+
# log to screen regardless
|
36
|
+
print(*string)
|
37
|
+
# log to file if that has been enabled
|
38
|
+
@logfile.write(string.join('').gsub(/\e\[(\d+)(;\d+)*m/, '')) if logging?
|
39
|
+
end
|
40
|
+
|
41
|
+
# mark these as private simply so that 'reek' wont flag as utility function.
|
42
|
+
private
|
43
|
+
|
30
44
|
def gitdir?(dirpath)
|
31
45
|
gitpath = dirpath + '/.git'
|
32
46
|
File.exist?(gitpath) && File.directory?(gitpath)
|
@@ -34,17 +48,11 @@ module Helpers
|
|
34
48
|
|
35
49
|
def show_time(duration)
|
36
50
|
time_taken = Time.at(duration).utc
|
37
|
-
time_taken.strftime('%-H hours, %-M Minutes and %-S seconds
|
51
|
+
time_taken.strftime('%-H hours, %-M Minutes and %-S seconds')
|
38
52
|
end
|
39
53
|
|
40
54
|
# we cant use --dump and --import on the same command line
|
41
55
|
def no_import_export
|
42
56
|
Trollop.die 'update_repo : Cannot specify both --dump and --import'
|
43
57
|
end
|
44
|
-
|
45
|
-
# print the specified summary metric, called from the footer.
|
46
|
-
def summary(which, color, event)
|
47
|
-
output = "#{which} #{event}"
|
48
|
-
print ' / ', output.send(color.to_sym) unless which.zero?
|
49
|
-
end
|
50
58
|
end
|
data/lib/update_repo/version.rb
CHANGED
data/lib/update_repo.rb
CHANGED
@@ -20,7 +20,10 @@ module UpdateRepo
|
|
20
20
|
# Class constructor. No parameters required.
|
21
21
|
# @return [void]
|
22
22
|
def initialize
|
23
|
-
@metrics = {
|
23
|
+
@metrics = { processed: 0, skipped: 0, failed: 0, updated: 0,
|
24
|
+
start_time: 0 }
|
25
|
+
@summary = { processed: 'green', updated: 'cyan', skipped: 'yellow',
|
26
|
+
failed: 'red' }
|
24
27
|
# read the options from Trollop and store in temp variable.
|
25
28
|
# we do it this way around otherwise if configuration file is missing it
|
26
29
|
# gives the error messages even on '--help' and '--version'
|
@@ -29,8 +32,7 @@ module UpdateRepo
|
|
29
32
|
# allows easy access to the configuration data
|
30
33
|
@config = Confoog::Settings.new(filename: CONFIG_FILE,
|
31
34
|
prefix: 'update_repo',
|
32
|
-
autoload: true,
|
33
|
-
autosave: false)
|
35
|
+
autoload: true, autosave: false)
|
34
36
|
# store the command line variables in a configuration variable
|
35
37
|
@config['cmd'] = temp_opt
|
36
38
|
config_error unless @config.status[:errors] == Status::INFO_FILE_LOADED
|
@@ -42,20 +44,39 @@ module UpdateRepo
|
|
42
44
|
# walk_repo.start
|
43
45
|
def start
|
44
46
|
String.disable_colorization = true unless param_set('color')
|
45
|
-
|
47
|
+
# make sure we dont have bad cmd-line parameter combinations ...
|
48
|
+
check_params
|
49
|
+
# print out our header ...
|
50
|
+
show_header unless dumping? || importing?
|
51
|
+
@config['location'].each do |loc|
|
52
|
+
recurse_dir(loc)
|
53
|
+
end
|
54
|
+
# print out an informative footer ...
|
55
|
+
footer unless dumping? || importing?
|
56
|
+
end
|
57
|
+
|
58
|
+
private
|
59
|
+
|
60
|
+
def check_params
|
61
|
+
setup_logfile if logging?
|
62
|
+
if dumping? && importing?
|
63
|
+
Trollop.die 'Sorry, you cannot specify both --dump and --import '.red
|
64
|
+
end
|
46
65
|
if importing?
|
47
66
|
Trollop.die "Sorry 'Import' functionality is not implemented yet".red
|
48
|
-
else
|
49
|
-
show_header
|
50
|
-
@config['location'].each do |loc|
|
51
|
-
recurse_dir(loc)
|
52
|
-
end
|
53
67
|
end
|
54
|
-
# print out an informative footer...
|
55
|
-
footer
|
56
68
|
end
|
57
69
|
|
58
|
-
|
70
|
+
def setup_logfile
|
71
|
+
filename = if param_set('timestamp')
|
72
|
+
'updaterepo-' + Time.new.strftime('%y%m%d-%H%M%S') + '.log'
|
73
|
+
else
|
74
|
+
'updaterepo.log'
|
75
|
+
end
|
76
|
+
# filename = 'updaterepo' + prefix + '.log'
|
77
|
+
@logfile = File.open(filename, 'w')
|
78
|
+
@logfile.sync = true
|
79
|
+
end
|
59
80
|
|
60
81
|
# Determine options from the command line and configuration file. Command
|
61
82
|
# line takes precedence
|
@@ -65,8 +86,8 @@ module UpdateRepo
|
|
65
86
|
|
66
87
|
def config_error
|
67
88
|
if @config.status[:errors] == Status::ERR_CANT_LOAD
|
68
|
-
|
69
|
-
|
89
|
+
print_log 'Note that the the default configuration file was '.red,
|
90
|
+
"changed to ~/#{CONFIG_FILE} from v0.4.0 onwards\n\n".red
|
70
91
|
end
|
71
92
|
exit 1
|
72
93
|
end
|
@@ -93,9 +114,10 @@ EOS
|
|
93
114
|
opt :dump, 'Dump a list of Directories and Git URL\'s to STDOUT in CSV format', default: false
|
94
115
|
opt :prune, "Number of directory levels to remove from the --dump output.\nOnly valid when --dump or -d specified", default: 0
|
95
116
|
opt :import, "Import a previous dump of directories and Git repository URL's,\n(created using --dump) then proceed to clone them locally.", default: false
|
117
|
+
opt :log, "Create a logfile of all program output to './update_repo.log'. Any older logs will be overwritten.", default: false
|
118
|
+
opt :timestamp, 'Timestamp the logfile instead of overwriting. Does nothing unless the --log option is also specified.', default: false
|
96
119
|
# opt :quiet, 'Only minimal output to the terminal', default: false
|
97
|
-
# opt :silent, 'Completely silent, no output to terminal at all.',
|
98
|
-
# default: false
|
120
|
+
# opt :silent, 'Completely silent, no output to terminal at all.', default: false
|
99
121
|
end
|
100
122
|
end
|
101
123
|
# rubocop:enable Metrics/MethodLength
|
@@ -110,8 +132,6 @@ EOS
|
|
110
132
|
next unless gitdir?(dir)
|
111
133
|
if dumping?
|
112
134
|
dump_repo(File.join(dirname, dir))
|
113
|
-
elsif importing?
|
114
|
-
# placeholder
|
115
135
|
else
|
116
136
|
notexception?(dir) ? update_repo(dir) : skip_repo(dir)
|
117
137
|
end
|
@@ -133,53 +153,57 @@ EOS
|
|
133
153
|
def show_header
|
134
154
|
# print an informative header before starting
|
135
155
|
# unless we are dumping the repo information
|
136
|
-
|
137
|
-
|
138
|
-
|
139
|
-
|
140
|
-
print "Command line is : #{@config['cmd']}\n"
|
156
|
+
print_log "\nGit Repo update utility (v", VERSION, ')',
|
157
|
+
" \u00A9 Grant Ramsay <seapagan@gmail.com>\n"
|
158
|
+
print_log "Using Configuration from '#{@config.config_path}'\n"
|
159
|
+
# print_log "Command line is : #{@config['cmd']}\n"
|
141
160
|
# list out the locations that will be searched
|
142
161
|
list_locations
|
143
162
|
# list any exceptions that we have from the config file
|
144
163
|
list_exceptions
|
145
164
|
# save the start time for later display in the footer...
|
146
165
|
@metrics[:start_time] = Time.now
|
147
|
-
|
166
|
+
print_log "\n" # blank line before processing starts
|
148
167
|
end
|
149
168
|
|
150
169
|
# print out a brief footer. This will be expanded later.
|
151
170
|
# @return [void]
|
152
171
|
def footer
|
153
|
-
# no footer if we are dumping the repo information
|
154
|
-
return if dumping?
|
155
172
|
duration = Time.now - @metrics[:start_time]
|
156
|
-
|
157
|
-
|
158
|
-
|
159
|
-
|
160
|
-
|
161
|
-
|
173
|
+
print_log "\nUpdates completed in ", show_time(duration).cyan
|
174
|
+
print_metrics
|
175
|
+
print_log " |\n\n"
|
176
|
+
# close the log file now as we are done, just to be sure ...
|
177
|
+
@logfile.close if @logfile
|
178
|
+
end
|
179
|
+
|
180
|
+
def print_metrics
|
181
|
+
@summary.each do |metric, color|
|
182
|
+
metric_value = @metrics[metric]
|
183
|
+
output = "#{metric_value} #{metric.capitalize}"
|
184
|
+
print_log ' | ', output.send(color.to_sym) unless metric_value.zero?
|
185
|
+
end
|
162
186
|
end
|
163
187
|
|
164
188
|
def list_exceptions
|
165
189
|
exceptions = @config['exceptions']
|
166
190
|
if exceptions
|
167
|
-
|
168
|
-
|
191
|
+
print_log "\nExclusions:".underline, ' ',
|
192
|
+
exceptions.join(', ').yellow, "\n"
|
169
193
|
end
|
170
194
|
end
|
171
195
|
|
172
196
|
def list_locations
|
173
|
-
|
197
|
+
print_log "\nRepo location(s):\n".underline
|
174
198
|
@config['location'].each do |loc|
|
175
|
-
|
199
|
+
print_log '-> ', loc.cyan, "\n"
|
176
200
|
end
|
177
201
|
end
|
178
202
|
|
179
203
|
def skip_repo(dirpath)
|
180
204
|
Dir.chdir(dirpath.chomp!('/')) do
|
181
205
|
repo_url = `git config remote.origin.url`.chomp
|
182
|
-
|
206
|
+
print_log '* Skipping ', Dir.pwd.yellow, " (#{repo_url})\n"
|
183
207
|
@metrics[:skipped] += 1
|
184
208
|
end
|
185
209
|
end
|
@@ -188,13 +212,14 @@ EOS
|
|
188
212
|
Dir.chdir(dirname.chomp!('/')) do
|
189
213
|
repo_url = `git config remote.origin.url`.chomp
|
190
214
|
do_update(repo_url)
|
191
|
-
@metrics[:
|
215
|
+
@metrics[:processed] += 1
|
192
216
|
end
|
193
217
|
end
|
194
218
|
|
195
219
|
def do_update(repo_url)
|
196
|
-
|
197
|
-
Open3.popen3('git pull') do |
|
220
|
+
print_log '* Checking ', Dir.pwd.green, " (#{repo_url})\n"
|
221
|
+
Open3.popen3('git pull') do |stdin, stdout, stderr, thread|
|
222
|
+
stdin.close
|
198
223
|
do_threads(stdout, stderr)
|
199
224
|
thread.join
|
200
225
|
end
|
@@ -205,12 +230,11 @@ EOS
|
|
205
230
|
Thread.new do
|
206
231
|
while (line = stream.gets)
|
207
232
|
if key == :err && line =~ /^fatal:/
|
208
|
-
|
233
|
+
print_log ' ', line.red
|
209
234
|
@metrics[:failed] += 1
|
210
235
|
else
|
211
|
-
|
212
|
-
|
213
|
-
@metrics[:updated] += 1 if line =~ /^From\shttps?:\/\//
|
236
|
+
print_log ' ', line.cyan
|
237
|
+
@metrics[:updated] += 1 if line =~ %r{^From\shttps?://}
|
214
238
|
end
|
215
239
|
end
|
216
240
|
end
|
@@ -220,7 +244,7 @@ EOS
|
|
220
244
|
def dump_repo(dir)
|
221
245
|
Dir.chdir(dir.chomp!('/')) do
|
222
246
|
repo_url = `git config remote.origin.url`.chomp
|
223
|
-
|
247
|
+
print_log "#{trunc_dir(dir, @config['cmd'][:prune])},#{repo_url}\n"
|
224
248
|
end
|
225
249
|
end
|
226
250
|
end
|
data/update_repo.gemspec
CHANGED
@@ -26,6 +26,7 @@ Gem::Specification.new do |spec|
|
|
26
26
|
spec.add_development_dependency 'pry'
|
27
27
|
spec.add_development_dependency 'fakefs'
|
28
28
|
spec.add_development_dependency 'json', '= 1.8.3'
|
29
|
+
spec.add_development_dependency 'tins', '= 1.6.0'
|
29
30
|
spec.add_development_dependency 'coveralls'
|
30
31
|
spec.add_development_dependency 'inch'
|
31
32
|
spec.add_development_dependency 'simplecov', '~> 0.10'
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: update_repo
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.7.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Grant Ramsay
|
8
8
|
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date: 2016-07-
|
11
|
+
date: 2016-07-29 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: bundler
|
@@ -94,6 +94,20 @@ dependencies:
|
|
94
94
|
- - '='
|
95
95
|
- !ruby/object:Gem::Version
|
96
96
|
version: 1.8.3
|
97
|
+
- !ruby/object:Gem::Dependency
|
98
|
+
name: tins
|
99
|
+
requirement: !ruby/object:Gem::Requirement
|
100
|
+
requirements:
|
101
|
+
- - '='
|
102
|
+
- !ruby/object:Gem::Version
|
103
|
+
version: 1.6.0
|
104
|
+
type: :development
|
105
|
+
prerelease: false
|
106
|
+
version_requirements: !ruby/object:Gem::Requirement
|
107
|
+
requirements:
|
108
|
+
- - '='
|
109
|
+
- !ruby/object:Gem::Version
|
110
|
+
version: 1.6.0
|
97
111
|
- !ruby/object:Gem::Dependency
|
98
112
|
name: coveralls
|
99
113
|
requirement: !ruby/object:Gem::Requirement
|