zypper-upgraderepo 1.0.2 → 1.5.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 25eb50066963aad6a37ce7c2d79410d0ef30a68e8dbc302e4a09f6c9589c15de
4
- data.tar.gz: ca2e0b7855cbd47ff45d41daef4ec3907e9813df77ead0ddd8e32fd37e4ff486
3
+ metadata.gz: 44bef40acdc725f7422911297413011d47e967d568497f74770ae162494a60dd
4
+ data.tar.gz: 4fa8b988dc188ee5deb97671ee31e99db1cf64efde819b8be2b5fef630b0b352
5
5
  SHA512:
6
- metadata.gz: e5c58c0ea4564541da066b599c9e882015e019328c84330f0bad4ccb3dcf99089628a40a9a1b5d3b0661996db86ce99c85d71d77138a765cfcabb313a888c098
7
- data.tar.gz: 6e4e59b92565921be94f45bc59efb7713cad2a5c40ce60096dd95195cc58401100411837470de7d76d0480d2284958f78a388bbd1f6135ade279a59d66e30cb0
6
+ metadata.gz: 6385cf9e04fcdd33ee544b64d64e16c123f750493d1a9b3b67eac84d167006debb05fada54488eaa7d5cbb414378d1ffd14e528d086cbe5b93af680ac643aa13
7
+ data.tar.gz: ca6a79d5387b76704b93994ff3e11bf0170f1950bbccad3335ff1564cde32d97edf55388c686858c75e594a3e46ac758ba2a66c1fadfba0b5b24157459240d31
@@ -0,0 +1,13 @@
1
+ # These are supported funding model platforms
2
+
3
+ github: [fabiomux]
4
+ #patreon: # Replace with a single Patreon username
5
+ #open_collective: # Replace with a single Open Collective username
6
+ #ko_fi: # Replace with a single Ko-fi username
7
+ #tidelift: # Replace with a single Tidelift platform-name/package-name e.g., npm/babel
8
+ #community_bridge: # Replace with a single Community Bridge project-name e.g., cloud-foundry
9
+ #liberapay: # Replace with a single Liberapay username
10
+ #issuehunt: # Replace with a single IssueHunt username
11
+ #otechie: # Replace with a single Otechie username
12
+ #custom: # Replace with up to 4 custom sponsorship URLs e.g., ['link1', 'link2']
13
+ custom: ['https://www.buymeacoffee.com/DCkNYFg']
data/Gemfile.lock CHANGED
@@ -1,39 +1,39 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- zypper-upgraderepo (1.0.2)
4
+ zypper-upgraderepo (1.5.0)
5
5
  iniparse
6
6
  minitar
7
7
 
8
8
  GEM
9
9
  remote: https://rubygems.org/
10
10
  specs:
11
- diff-lcs (1.3)
12
- iniparse (1.4.4)
13
- minitar (0.6.1)
14
- rake (10.5.0)
15
- rspec (3.7.0)
16
- rspec-core (~> 3.7.0)
17
- rspec-expectations (~> 3.7.0)
18
- rspec-mocks (~> 3.7.0)
19
- rspec-core (3.7.1)
20
- rspec-support (~> 3.7.0)
21
- rspec-expectations (3.7.0)
11
+ diff-lcs (1.4.4)
12
+ iniparse (1.5.0)
13
+ minitar (0.9)
14
+ rake (13.0.1)
15
+ rspec (3.9.0)
16
+ rspec-core (~> 3.9.0)
17
+ rspec-expectations (~> 3.9.0)
18
+ rspec-mocks (~> 3.9.0)
19
+ rspec-core (3.9.2)
20
+ rspec-support (~> 3.9.3)
21
+ rspec-expectations (3.9.2)
22
22
  diff-lcs (>= 1.2.0, < 2.0)
23
- rspec-support (~> 3.7.0)
24
- rspec-mocks (3.7.0)
23
+ rspec-support (~> 3.9.0)
24
+ rspec-mocks (3.9.1)
25
25
  diff-lcs (>= 1.2.0, < 2.0)
26
- rspec-support (~> 3.7.0)
27
- rspec-support (3.7.1)
26
+ rspec-support (~> 3.9.0)
27
+ rspec-support (3.9.3)
28
28
 
29
29
  PLATFORMS
30
30
  ruby
31
31
 
32
32
  DEPENDENCIES
33
- bundler (~> 1.16)
34
- rake (~> 10.0)
33
+ bundler (~> 2.0)
34
+ rake (~> 13.0)
35
35
  rspec (~> 3.0)
36
36
  zypper-upgraderepo!
37
37
 
38
38
  BUNDLED WITH
39
- 1.16.2
39
+ 2.1.4
data/README.md CHANGED
@@ -17,15 +17,15 @@ If you want to install it as zypper plugin watch the _zypper-upgraderepo-plugin_
17
17
 
18
18
  To check the availability of the current repositories:
19
19
 
20
- $ zypper-upgraderepo -c
20
+ $ zypper-upgraderepo --check-current
21
21
 
22
22
  To check the availability of the next version repositories:
23
23
 
24
- $ zypper-upgraderepo -n
24
+ $ zypper-upgraderepo --check-next
25
25
 
26
26
  To upgrade the repositories to the next version:
27
27
 
28
- $ sudo zypper-upgraderepo -u
28
+ $ sudo zypper-upgraderepo --upgrade
29
29
 
30
30
  ## Get help
31
31
 
@@ -36,6 +36,10 @@ Where to start:
36
36
  More Help:
37
37
 
38
38
  - The wiki page: https://github.com/fabiomux/zypper-upgraderepo
39
+ - openSUSE Lizards: https://lizards.opensuse.org/2018/08/07/zypper-upgraderepo-plugin-is-here/
40
+
41
+ ## Related projects
42
+
39
43
  - zypper-upgraderepo-plugin project: https://github.com/fabiomux/zypper-upgraderepo-plugin
40
44
 
41
45
  ## Contributing
@@ -1,6 +1,10 @@
1
1
  require 'zypper/upgraderepo/repository'
2
+ require 'zypper/upgraderepo/request'
2
3
  require 'zypper/upgraderepo/os_release'
3
4
  require 'zypper/upgraderepo/utils'
5
+ require 'zypper/upgraderepo/view'
6
+ require 'zlib'
7
+ require 'minitar'
4
8
 
5
9
 
6
10
  module Zypper
@@ -9,13 +13,23 @@ module Zypper
9
13
  class Builder
10
14
  def initialize(options)
11
15
  @os_release = OsRelease.new(options)
12
- @repos = RepositoryList.new(options)
16
+ @repos = RepositoryList.new(options).resolve_variables!(@os_release.current)
13
17
  @print_hint = options.hint
18
+ @view_class = Zypper::Upgraderepo::View.const_get options.view.to_s.capitalize
19
+
20
+ @backup_path = options.backup_path
21
+
22
+ @exit_on_fail = options.exit_on_fail
14
23
  end
15
24
 
16
25
  def backup
17
- @repos.backup
18
- Messages.ok 'Repository backup executed!'
26
+ filename = File.join(@backup_path, "repos-backup-#{Time.now.to_s.delete(': +-')[0..-5]}.tgz")
27
+
28
+ raise InvalidWritePermissions, filename unless File.writable? @backup_path
29
+
30
+ Minitar.pack(RepositoryList::REPOSITORY_PATH, Zlib::GzipWriter.new(File.open(filename, 'wb')))
31
+
32
+ Messages.ok "Backup file generated at #{filename.bold.green}"
19
33
  end
20
34
 
21
35
  def check_current
@@ -23,47 +37,81 @@ module Zypper
23
37
  end
24
38
 
25
39
  def check_next
26
- @repos.upgrade(@os_release.next) unless @os_release.last?
40
+ raise AlreadyUpgraded, 'latest' if @os_release.last?
41
+ @repos.upgrade!(@os_release.next)
27
42
  check_repos(@os_release.next)
28
43
  end
29
44
 
30
45
  def check_to
31
- @repos.upgrade(@os_release.custom)
46
+ @repos.upgrade!(@os_release.custom)
32
47
  check_repos(@os_release.custom)
33
48
  end
34
49
 
35
50
  def upgrade
36
- @repos.upgrade(@os_release.next) unless @os_release.last?
37
- @repos.save
38
- Messages.ok 'Repositories upgraded!'
51
+ raise AlreadyUpgraded, 'latest' if @os_release.last?
52
+ @repos.upgrade!(@os_release.next)
53
+ upgrade_repos(@os_release.next)
39
54
  end
40
55
 
41
56
  def upgrade_to
42
- @repos.upgrade(@os_release.custom)
43
- @repos.save
44
- Messages.ok 'Repositories upgraded!'
57
+ raise AlreadyUpgraded, @os_release.custom if @os_release.current?(@os_release.custom)
58
+ @repos.upgrade!(@os_release.custom)
59
+ upgrade_repos(@os_release.custom)
60
+ end
61
+
62
+ def reset
63
+ upgrade_repos(@os_release.current)
45
64
  end
46
65
 
47
66
 
48
67
  private
49
68
 
50
69
  def check_repos(version)
51
- Messages.header(@repos.max_col)
52
- @repos.list.each_with_index do |r, i|
53
- Messages.separator
54
- if r.available?
55
- Messages.available i.next, r.name, r.url, @repos.max_col
56
- elsif r.redirected?
57
- Messages.redirected i.next, r.name, r.url, @repos.max_col, r.redirected_to
58
- elsif r.not_found?
59
- if @print_hint
60
- Messages.alternative i.next, r.name, r.url, @repos.max_col, r.evaluate_alternative(version)
61
- else
62
- Messages.not_found i.next, r.name, r.url, @repos.max_col
70
+ @view_class.header(@repos.max_col)
71
+
72
+ @repos.each_with_number do |repo, num|
73
+
74
+ @view_class.separator
75
+
76
+ if repo.available?
77
+ @view_class.available num, repo, @repos.max_col
78
+ else
79
+ raise UnableToUpgrade, { num: num, repo: repo } if @exit_on_fail
80
+ if repo.redirected?
81
+ @view_class.redirected num, repo, @repos.max_col, repo.redirected_to
82
+ elsif repo.not_found?
83
+ if @print_hint
84
+ @view_class.alternative num, repo, @repos.max_col, repo.evaluate_alternative(version)
85
+ else
86
+ @view_class.not_found num, repo, @repos.max_col
87
+ end
88
+ elsif repo.timeout?
89
+ @view_class.timeout num, repo, @repos.max_col
63
90
  end
64
91
  end
65
92
  end
66
- Messages.footer
93
+
94
+ @view_class.footer
95
+ end
96
+
97
+ def upgrade_repos(version)
98
+ @view_class.header(@repos.max_col, true)
99
+
100
+ @repos.each_with_number do |repo, num|
101
+
102
+ @view_class.separator
103
+
104
+ if repo.upgraded?
105
+ @view_class.upgraded num, repo, @repos.max_col
106
+ else
107
+ @view_class.untouched num, repo, @repos.max_col
108
+ end
109
+ end
110
+
111
+ @view_class.separator
112
+
113
+ @repos.save
114
+ Messages.ok 'Repositories upgraded!'
67
115
  end
68
116
 
69
117
  end
@@ -13,13 +13,21 @@ module Zypper
13
13
  options = OpenStruct.new
14
14
  options.operation = :check_current
15
15
  options.backup_path = ENV['HOME']
16
- options.only_enabled = true
16
+ options.only_enabled = false
17
17
  options.alias = true
18
18
  options.name = true
19
19
  options.hint = true
20
20
  options.overrides = {}
21
21
  options.version = nil
22
-
22
+ options.sort_by = :alias
23
+ options.view = :table
24
+ options.only_repo = nil
25
+ options.timeout = 10.0
26
+ options.exit_on_fail = false
27
+ options.overrides_filename = nil
28
+ options.only_invalid = false
29
+ options.only_protocols = nil
30
+
23
31
  opt_parser = OptionParser.new do |opt|
24
32
 
25
33
  if ENV['ZYPPER_UPGRADEREPO']
@@ -50,6 +58,10 @@ module Zypper
50
58
  options.operation = :check_to
51
59
  end
52
60
 
61
+ opt.on('-R', '--reset', 'Reset the repositories to the current OS version.') do |v|
62
+ options.operation = :reset
63
+ end
64
+
53
65
  opt.on('-u', '--upgrade', 'Upgrade to the last version available') do |o|
54
66
  options.operation = :upgrade
55
67
  end
@@ -62,26 +74,81 @@ module Zypper
62
74
  opt.separator ''
63
75
  opt.separator 'Options:'
64
76
 
65
- opt.on('--[no-]only-enabled', 'Include or not the disabled repositories') do |o|
66
- options.only_enabled = o
77
+ opt.on('--no-name', 'Don\'t upgrade the name') do |o|
78
+ options.name = false
79
+ end
80
+
81
+ opt.on('--no-alias', 'Don\'t upgrade the alias') do |o|
82
+ options.alias = false
83
+ end
84
+
85
+ opt.on('--no-hint', 'Don\'t find a working URL when the current is invalid') do |o|
86
+ options.hint = false
87
+ end
88
+
89
+ opt.on('--override-url <NUMBER>,<URL>', Array, 'Overwrite the repository NUMBER with URL') do |r|
90
+ options.overrides[r[0].to_i] = r[1]
67
91
  end
68
92
 
69
- opt.on('--[no-]name', 'Upgrade or not the name') do |o|
70
- options.name = o
93
+ opt.on('--load-overrides <FILENAME>', 'Check the URLs in the exported FILENAME') do |f|
94
+ options.overrides_filename = f
95
+ end
96
+
97
+ opt.on('--exit-on-fail', 'Exit with error when a repository upgrade check fails') do |o|
98
+ options.exit_on_fail = true
99
+ end
100
+
101
+ opt.on('--timeout <SECONDS>', "Adjust the waiting SECONDS used to catch an HTTP Timeout Error (Default: #{options.timeout})") do |o|
102
+ options.timeout = o.to_f
103
+ end
104
+
105
+ opt.separator ''
106
+ opt.separator 'Filter options:'
107
+
108
+ opt.on('--only-enabled', 'Include only the enabled repositories') do |o|
109
+ options.only_enabled = true
71
110
  end
72
111
 
73
- opt.on('--[no-]alias', 'Upgrade or not the alias') do |o|
74
- options.alias = o
112
+ opt.on('--only-repo <NUMBER>[,NUMBER2,...]', 'Include only the repositories specified by NUMBER') do |o|
113
+ options.only_repo = o.split(',').map(&:to_i)
75
114
  end
76
115
 
77
- opt.on('--[no-]hint', 'Suggest a new url when the current is not found') do |o|
78
- options.hint = o
116
+ opt.on('--only-invalid', 'Show only invalid repositories') do |o|
117
+ options.only_invalid = true
79
118
  end
80
119
 
81
- opt.on('--override-url <NUMBER>,<URL>', Array, 'Overwrite the repository\'s url NUMBER with URL') do |r|
82
- options.overrides[r[0]] = r[1]
120
+ opt.on('--only-protocols <PROTOCOL>[,<PROTOCOL2>,...]', Array, "Show only from protocols (supported: #{Request.protocols.join(',')})") do |o|
121
+ options.only_protocols = o
83
122
  end
84
123
 
124
+ opt.separator ''
125
+ opt.separator 'View options:'
126
+
127
+ opt.on('--sort-by-alias', 'Sort repositories by alias (Default)') do |o|
128
+ options.sort_by = :alias
129
+ end
130
+
131
+ opt.on('--sort-by-name', 'Sort repositories by name') do |o|
132
+ options.sort_by = :name
133
+ end
134
+
135
+ opt.on('--sort-by-priority', 'Sort repositories by priority') do |o|
136
+ options.sort_by = :priority
137
+ end
138
+
139
+ opt.on('--ini', 'Output the result in Ini format') do |o|
140
+ options.view = :ini
141
+ end
142
+
143
+ opt.on('--quiet', 'Quiet mode, show only error messages') do |o|
144
+ options.view = :quiet
145
+ end
146
+
147
+ opt.on('--report', 'View the data as report') do |o|
148
+ options.view = :report
149
+ end
150
+
151
+
85
152
  unless ENV['ZYPPER_UPGRADEREPO']
86
153
  opt.separator ''
87
154
  opt.separator 'Other:'
@@ -98,7 +165,7 @@ module Zypper
98
165
  end
99
166
 
100
167
  end
101
-
168
+
102
169
  if ARGV.empty?
103
170
  puts opt_parser; exit
104
171
  else
@@ -111,14 +178,14 @@ module Zypper
111
178
  end
112
179
 
113
180
 
114
- class CLI
181
+ class CLI
115
182
  def self.start
116
183
  begin
117
184
  options = OptParseMain.parse(ARGV)
118
185
  Upgraderepo::Builder.new(options).send(options.operation)
119
186
  rescue => e
120
187
  Messages.error e
121
- exit 1
188
+ exit e.error_code
122
189
  end
123
190
  end
124
191
  end
@@ -8,7 +8,7 @@ module Zypper
8
8
 
9
9
  attr_reader :custom
10
10
 
11
- OS_VERSIONS = ['13.1', '13.2', '42.1', '42.2', '42.3', '15.0']
11
+ OS_VERSIONS = ['13.1', '13.2', '42.1', '42.2', '42.3', '15.0', '15.1', '15.2', '15.3']
12
12
 
13
13
 
14
14
  def initialize(options)
@@ -24,7 +24,6 @@ module Zypper
24
24
 
25
25
  if options.version
26
26
  raise InvalidVersion, options.version unless OS_VERSIONS.include?(options.version)
27
- raise AlreadyUpgraded, options.version unless OS_VERSIONS.index(options.version) != @current_idx
28
27
  @custom = options.version
29
28
  end
30
29
  end
@@ -60,6 +59,10 @@ module Zypper
60
59
  def valid?(version)
61
60
  OS_VERSIONS.include? version
62
61
  end
62
+
63
+ def current?(version)
64
+ OS_VERSIONS.index(version) == @current_idx
65
+ end
63
66
  end
64
67
 
65
68
 
@@ -1,47 +1,76 @@
1
1
  require 'iniparse'
2
- require 'net/http'
3
- require 'zlib'
4
- require 'minitar'
5
2
 
6
3
  module Zypper
7
4
  module Upgraderepo
8
5
 
9
6
 
10
7
  class RepositoryList
8
+
9
+ REPOSITORY_PATH = '/etc/zypp/repos.d'
10
+
11
11
  attr_reader :list, :max_col
12
12
 
13
13
  def initialize(options)
14
14
  @alias = options.alias
15
15
  @name = options.name
16
+ @only_repo = options.only_repo
17
+ @only_enabled = options.only_enabled
18
+ @only_invalid = options.only_invalid
19
+ @only_protocols = options.only_protocols
16
20
  @overrides = options.overrides
21
+ @upgrade_options = {alias: options.alias, name: options.name}
17
22
  @list = []
18
- @backup_path = options.backup_path
19
23
 
20
- Dir.glob('/etc/zypp/repos.d/*.repo').sort.each do |i|
21
- r = Repository.new(i)
22
- next if options.only_enabled && (!r.enabled?)
24
+ Dir.glob(File.join(REPOSITORY_PATH, '*.repo')).each do |i|
25
+ r = Request.build(Repository.new(i), options.timeout)
23
26
  @list << r
24
27
  end
25
- @max_col = @list.max_by { |x| x.name.length }.name.length
28
+ @max_col = @list.max_by { |r| r.name.length }.name.length
29
+
30
+ @list = @list.sort_by { |r| r.alias }.map.with_index(1) { |r, i| { num: i, repo: r } }
31
+
32
+ @list.sort_by! { |x| x[:repo].send(options.sort_by) } if options.sort_by != :alias
33
+
34
+ load_overrides(options.filename) if options.filename
35
+ end
36
+
37
+ def only_enabled?
38
+ @only_enabled
39
+ end
40
+
41
+ def upgrade!(version)
42
+ each_with_number(only_invalid: false) do |repo, num|
43
+ repo.upgrade! version, @upgrade_options.merge(url_override: @overrides[num])
44
+ repo.cache!
45
+ end
26
46
  end
27
47
 
28
- def backup
29
- filename = File.join(@backup_path, "repos-backup-#{Time.now.to_s.delete(': +-')[0..-5]}.tgz")
30
- raise InvalidPermissions, filename unless File.writable? @backup_path
31
- Minitar.pack('/etc/zypp/repos.d',
32
- Zlib::GzipWriter.new(File.open(filename, 'wb')))
48
+ def each_with_number(options = {})
49
+ only_repo = options[:only_repo].nil? ? @only_repo : options[:only_repo]
50
+ only_enabled = options[:only_enabled].nil? ? @only_enabled : options[:only_enabled]
51
+ only_invalid = options[:only_invalid].nil? ? @only_invalid : options[:only_invalid]
52
+ only_protocols = options[:only_protocols].nil? ? @only_protocols : options[:only_protocols]
53
+
54
+ @list.each do |x|
55
+ next if only_repo && !only_repo.include?(x[:num])
56
+ next if only_enabled && !x[:repo].enabled?
57
+ next if only_invalid && x[:repo].available?
58
+ next if only_protocols && (!only_protocols.include?(x[:repo].protocol))
59
+
60
+ yield x[:repo], x[:num] if block_given?
61
+ end
33
62
  end
34
63
 
35
- def upgrade(version)
36
- @list.each_with_index do |repo, i|
37
- if @overrides.has_key? i.next.to_s
38
- repo.url = @overrides[i.next.to_s]
39
- else
40
- repo.url = repo.url.gsub(/\d\d\.\d/, version)
64
+ def resolve_variables!(version)
65
+ each_with_number do |r|
66
+ if r.url =~ /\$/
67
+ r.url = r.url.gsub(/\$releasever_major/, version.split('.')[0])
68
+ .gsub(/\$releasever_minor/, version.split('.')[1])
69
+ .gsub(/\$releasever/, version)
41
70
  end
42
- repo.alias = repo.alias.gsub(/\d\d\.\d/, version) if @alias
43
- repo.name = repo.name.gsub(/\d\d\.\d/, version) if @name
44
71
  end
72
+
73
+ self
45
74
  end
46
75
 
47
76
  def save
@@ -49,23 +78,50 @@ module Zypper
49
78
  i.save
50
79
  end
51
80
  end
81
+
82
+
83
+ private
84
+
85
+ def load_overrides(filename)
86
+ raise FileNotFound, filename unless File.exist?(filename)
87
+ ini = IniParse.parse(File.read(filename))
88
+ each_with_number(only_invalid: false) do |repo, num|
89
+ if x = ini["repository_#{num}"]
90
+ repo.enable!(x['enabled'])
91
+ raise UnmatchingOverrides, { num: num, ini: x, repo: repo } if repo.url != x['old_url']
92
+ if (@repos.only_enabled?)
93
+ raise MissingOverride, { num: num, ini: x } unless x['url'] || x['enabled'] =~ /no|false|0/i
94
+ else
95
+ raise MissingOverride, { num: num, ini: x } unless x['url']
96
+ end
97
+ @overrides[num] = x['url'] if x['url']
98
+ end
99
+ end
100
+ end
101
+
52
102
  end
53
103
 
54
104
 
55
105
  class Repository
56
- attr_reader :filename
57
-
106
+ attr_reader :filename, :old_url, :old_alias, :old_name
107
+
58
108
  def initialize(filename)
59
109
  @filename = filename
60
110
  @repo = IniParse.parse(File.read(filename))
61
- @key = get_key
62
- @res = nil
111
+ @key = get_key
112
+ @old_url = nil
113
+ @old_name = nil
114
+ @old_alias = nil
63
115
  end
64
116
 
65
117
  def enabled?
66
118
  @repo[@key]['enabled'].to_i == 1
67
119
  end
68
120
 
121
+ def enable!(value = true)
122
+ @repo[@key]['enabled'] = (value.to_s =~ /true|1|yes/i) ? 1 : 0
123
+ end
124
+
69
125
  def type
70
126
  @repo[@key]['type']
71
127
  end
@@ -78,6 +134,10 @@ module Zypper
78
134
  @repo[@key]['name'] = value
79
135
  end
80
136
 
137
+ def priority
138
+ @repo[@key]['priority'] || 99
139
+ end
140
+
81
141
  def url
82
142
  @repo[@key]['baseurl']
83
143
  end
@@ -86,6 +146,18 @@ module Zypper
86
146
  @repo[@key]['baseurl'] = value
87
147
  end
88
148
 
149
+ def protocol
150
+ URI(url.to_s).scheme
151
+ end
152
+
153
+ def unversioned?
154
+ (url =~ /\d\d\.\d/).nil?
155
+ end
156
+
157
+ def versioned?
158
+ !unversioned?
159
+ end
160
+
89
161
  def alias
90
162
  @key
91
163
  end
@@ -95,75 +167,45 @@ module Zypper
95
167
  @key = get_key
96
168
  end
97
169
 
98
- def available?
99
- ping.is_a?(Net::HTTPSuccess)
100
- end
170
+ def upgrade!(version, args = {})
171
+ @old_url ||= self.url
172
+ @old_alias ||= self.alias
173
+ @old_name ||= self.name
101
174
 
102
- def redirected?
103
- ping.is_a?(Net::HTTPRedirection)
104
- end
175
+ if args[:url_override]
176
+ self.url = args[:url_override]
177
+ else
178
+ self.url = self.url.gsub(/\d\d\.\d/, version)
179
+ end
105
180
 
106
- def redirected_to
107
- ping['location']
181
+ self.alias = self.alias.gsub(/\d\d\.\d/, version) if args[:alias]
182
+ self.name = self.name.gsub(/\d\d\.\d/, version) if args[:name]
108
183
  end
109
184
 
110
- def not_found?
111
- ping.is_a?(Net::HTTPNotFound)
185
+ def upgraded?(item = :url)
186
+ (!self.send("old_#{item}").nil?) && (self.send("old_#{item}") != self.send(item))
112
187
  end
113
188
 
114
189
  def save
115
- raise InvalidPermissions, @filename unless File.writable? @filename
116
- @repo.save(@filename)
190
+ raise InvalidWritePermissions, @filename unless File.writable? @filename
191
+ process, pid = libzypp_process
192
+ raise SystemUpdateRunning, { pid: pid, process: process } if pid
193
+ @repo.save(@filename)
117
194
  end
118
195
 
119
- def evaluate_alternative(version)
120
- if url =~ /dl\.google\.com/
121
- return { url: '', message: 'Just Google security, use this repo anyway ;)'}
122
- elsif not_found?
123
- return traverse_url(URI(url.clone), version)
124
- elsif redirected?
125
- return { url: redirected_to, message: 'Redirected to:' }
126
- end
127
- end
128
196
 
129
197
  private
130
198
 
131
- def ping(uri = URI(url), force = false)
132
- begin
133
- @res = Net::HTTP.get_response(uri) if @res.nil? || force
134
- rescue SocketError
135
- raise NoConnection
136
- end
137
- @res
199
+ def libzypp_process
200
+ libpath = `ldd /usr/bin/zypper | grep "libzypp.so"`.split(' => ')[1].split(' ').shift
201
+ process = `sudo lsof #{libpath} | tail -n 1`
202
+ process, pid = process.split(' ')
203
+ [process, pid]
138
204
  end
139
205
 
140
206
  def get_key
141
207
  @repo.to_hash.keys.delete_if {|k| k == '0'}.pop
142
208
  end
143
-
144
- def traverse_url(uri, version)
145
- uri.path = File.dirname(uri.path)
146
-
147
- return {url: '', message: 'None, try to find it manually'} if uri.path == '/'
148
-
149
- uri.path += '/'
150
- ping(uri, true)
151
-
152
- if not_found?
153
- return traverse_url(uri, version)
154
- elsif available?
155
- return {url: uri.to_s, message: 'Override with this one' } if uri.path =~ Regexp.new(version)
156
-
157
- path = ping.body.to_s.scan(Regexp.new("href=\"[^\"]*#{version}[^\"]*\"")).uniq
158
- unless path.empty?
159
- uri.path += "#{path.pop.scan(/href="(.*)"/).pop.pop }"
160
- return {url: uri.to_s, message: 'Override with this one' }
161
- end
162
-
163
- return {url: url, message: 'Can\'t find anything similar, try manually!' }
164
- end
165
-
166
- end
167
209
  end
168
210
 
169
211