forked from openSUSE/openSUSE-release-tools
-
Notifications
You must be signed in to change notification settings - Fork 0
/
obs-to-vagrantcloud.rb
143 lines (113 loc) · 4.15 KB
/
obs-to-vagrantcloud.rb
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
# frozen_string_literal: true
require 'vagrant_cloud'
require 'down/net_http'
require 'http'
require 'optparse'
require 'optparse/uri'
require 'open-uri'
require 'fileutils'
def ensure_box_present(box_from_obs, org)
matching_boxes = org.boxes.select { |b| b.name == box_from_obs['name'] }
matching_box = nil
if matching_boxes.empty?
matching_box = org.add_box(box_from_obs['name'])
matching_box.private = false
matching_box.description = box_from_obs['description']
matching_box.short_description = box_from_obs['short_description']
elsif matching_boxes.length > 1
raise "Got #{matching_boxes.length} matching boxes, but should have gotten at most one"
else
matching_box = matching_boxes[0]
end
matching_box
end
def link_box(box_from_obs, org)
matching_box = ensure_box_present(box_from_obs, org)
matching_box.versions.each(&:delete)
matching_box.versions = []
matching_box.save
box_from_obs['versions'].each do |version|
ver = matching_box.add_version(version['version'])
ver.description = version['description']
version['providers'].each do |provider|
prov = ver.add_provider(provider['name'])
prov.url = provider['url']
end
ver.save
ver.release
end
matching_box.save
matching_box
end
##
# Uploads the box specified in the hash box_from_obs to VagrantCloud using the
# supplied organization.
def upload_non_existent_boxes(box_from_obs, organization, provider_to_upload)
matching_box = ensure_box_present(box_from_obs, organization)
box_from_obs['versions'].each do |version|
matching_versions = matching_box.versions.select { |v| v.version == version['version'] }
matching_version = nil
if matching_versions.length == 1
matching_version = matching_versions[0]
elsif matching_versions.empty?
matching_box.save
matching_version = matching_box.add_version(version['version'])
matching_version.description = version['description']
else
raise "Got #{matching_versions.length} matching versions, but should have gotten one or none"
end
provider_added = false
not_present_providers = version['providers'].select do |prov_from_obs|
matching_version.providers.select { |p| p.name == prov_from_obs['name'] }.empty?
end
unless provider_to_upload.nil?
not_present_providers = not_present_providers.select { |p| p['name'] == provider_to_upload }
end
not_present_providers.each do |provider|
prov = matching_version.add_provider(provider['name'])
begin
box_dest = Down::NetHttp.download(provider['url'], max_redirects: 20)
matching_box.save
prov.upload(path: box_dest.path)
provider_added = true
ensure
box_dest.close
box_dest.unlink
end
end
matching_version.release if provider_added && !matching_version.released?
end
matching_box
end
env_var = 'ATLAS_TOKEN'
raise "Environment variable #{env_var} is required" if ENV[env_var].nil?
options = {}
OptionParser.new do |opts|
opts.on('--url URI', 'URL to json file published on OBS') do |u|
options[:url] = u
end
opts.on('--organization ORG', 'organization/publisher of the vagrant box') do |p|
options[:publisher] = p
end
opts.on('-n NAME', '--new-box-name NAME', 'alternative name for the Vagrant box') do |n|
options[:name] = n
end
opts.on('-p PROVIDER', '--provider PROVIDER', 'only upload the supplied provider (unsupported for linking!)') do |p|
options[:provider] = p
end
opts.on('-l', '--link', 'just link the box to from OBS and don\'t upload it') do
options[:link] = true
end
end.parse!
raise 'An organization must be provided' if options[:publisher].nil?
options[:link] = false if options[:link].nil?
raise 'Linking only a single provider is not supported' if options[:link] && !options[:provider].nil?
box_json = JSON.parse(HTTP.get(options[:url]))
account = VagrantCloud::Account.new(access_token: ENV[env_var])
publisher = account.organization(name: options[:publisher])
box_json['name'] = options[:name] unless options[:name].nil?
if options[:link]
link_box(box_json, publisher)
else
upload_non_existent_boxes(box_json, publisher, options[:provider])
end