foreman_fog_proxmox 0.5.4 → 0.5.5
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.
Potentially problematic release.
This version of foreman_fog_proxmox might be problematic. Click here for more details.
- checksums.yaml +4 -4
- data/README.md +10 -6
- data/app/assets/javascripts/foreman_fog_proxmox/proxmox_vm.js +10 -4
- data/app/assets/javascripts/foreman_fog_proxmox/proxmox_vm_server.js +60 -45
- data/app/helpers/proxmox_container_helper.rb +2 -1
- data/app/helpers/proxmox_form_helper.rb +19 -14
- data/app/helpers/proxmox_server_helper.rb +5 -5
- data/app/helpers/proxmox_vm_helper.rb +12 -0
- data/app/models/foreman_fog_proxmox/proxmox.rb +9 -3
- data/app/views/compute_resources_vms/form/proxmox/_add_vm_type_to_volumes_edit.html.erb +22 -35
- data/app/views/compute_resources_vms/form/proxmox/container/_volume_mp.html.erb +1 -0
- data/app/views/compute_resources_vms/form/proxmox/server/_config.html.erb +1 -0
- data/app/views/compute_resources_vms/form/proxmox/server/_volume.html.erb +1 -1
- data/lib/foreman_fog_proxmox/version.rb +1 -1
- data/test/unit/foreman_fog_proxmox/helpers/proxmox_server_helper_test.rb +12 -1
- metadata +6 -6
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: ca619ec359deaafb7ae8d9226bd0db7213a8f8276b27c24e39d3f4549744d759
|
4
|
+
data.tar.gz: 674603da5a60bf493462eaff2f9ac55637b908ee557cb2d026cdba006f17d1df
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: a5bc188c202ac4c0a067c001949ae64666c914000a2d2eff3bd49554f0be033bc5b5bcafddcfa9aeaebc9f282c7d0908237c3dfed801bbd8109fa7a5f79a757f
|
7
|
+
data.tar.gz: 044cc2a7d66fb8cddb3332d0fe98160e77a6bb0a71aec979334692197e4e406d2866bb84c8e1dde032797541c96f267a3126024e9520d28f87ceb0eb4f09a4a3
|
data/README.md
CHANGED
@@ -17,7 +17,7 @@ If you like it and need more features you can [support](SUPPORT.md) it.
|
|
17
17
|
Tested with:
|
18
18
|
|
19
19
|
* Foreman >= 1.17 and < 1.20
|
20
|
-
* Fog-proxmox >= 0.5.
|
20
|
+
* Fog-proxmox >= 0.5.3
|
21
21
|
* Proxmox >= 5.1
|
22
22
|
* Ruby >= 2.3
|
23
23
|
|
@@ -101,9 +101,9 @@ Please see the Foreman manual for complete instructions:
|
|
101
101
|
|
102
102
|
### Prerequisites
|
103
103
|
|
104
|
-
You need a Proxmox VE >= 5.1 server running.
|
105
|
-
|
106
|
-
You also need nodejs in your dev machine to run webpack-dev-server.
|
104
|
+
* You need a Proxmox VE >= 5.1 server running.
|
105
|
+
* You need ruby >= 2.3. You can install it with [rbenv](https://github.com/rbenv/rbenv).
|
106
|
+
* You also need nodejs in your dev machine to run webpack-dev-server. You can install it with [nvm](https://github.com/creationix/nvm).
|
107
107
|
|
108
108
|
### Platform
|
109
109
|
|
@@ -121,18 +121,22 @@ git checkout tags/1.17.3
|
|
121
121
|
|
122
122
|
```ruby
|
123
123
|
gem 'foreman_fog_proxmox', :path => '/your_path_to/foreman_fog_proxmox'
|
124
|
+
gem 'fog-proxmox', :path => '/your_path_to/fog-proxmox' # optional if you need to modify fog-proxmox code too
|
125
|
+
gem 'ruby-debug-ide' # dev
|
126
|
+
gem 'debase' # dev
|
127
|
+
gem 'simplecov' # test
|
124
128
|
```
|
125
129
|
|
126
130
|
* In foreman directory, install dependencies:
|
127
131
|
|
128
132
|
```shell
|
129
|
-
bundle install
|
133
|
+
bundle install --without libvirt postgresql mysql2
|
130
134
|
```
|
131
135
|
|
132
136
|
* Configure foreman settings:
|
133
137
|
|
134
138
|
```shell
|
135
|
-
cp config/settings.yaml.
|
139
|
+
cp config/settings.yaml.test config/settings.yaml
|
136
140
|
```
|
137
141
|
|
138
142
|
* Install foreman database (sqlite is default in rails development):
|
@@ -50,21 +50,26 @@ function toggleVolumes(selected){
|
|
50
50
|
div_server.show();
|
51
51
|
a_container.hide();
|
52
52
|
a_server.show();
|
53
|
-
|
53
|
+
break;
|
54
54
|
case 'lxc':
|
55
55
|
div_container.show();
|
56
56
|
div_server.hide();
|
57
57
|
a_container.show();
|
58
58
|
a_server.hide();
|
59
|
-
|
59
|
+
break;
|
60
|
+
default:
|
61
|
+
console.log("unkown type="+selected);
|
62
|
+
break;
|
60
63
|
}
|
61
64
|
}
|
62
65
|
|
63
66
|
function toggleFieldset(fieldset, index, fieldsets){
|
64
|
-
var server_input_hidden = $("div[id^='server_volumes']" + "
|
65
|
-
var container_input_hidden = $("div[id^='container_volumes']" + "
|
67
|
+
var server_input_hidden = $("div[id^='server_volumes']" + " + input:hidden");
|
68
|
+
var container_input_hidden = $("div[id^='container_volumes']" + " + input:hidden");
|
69
|
+
var removable_input_hidden = $("div.removable-item[style='display: none;']" + " + input:hidden");
|
66
70
|
var server_fieldset = $("fieldset[id^='server_"+fieldset.id+"']");
|
67
71
|
var container_fieldset = $("fieldset[id^='container_"+fieldset.id+"']");
|
72
|
+
removable_input_hidden.attr('disabled','disabled');
|
68
73
|
switch (fieldset.selected) {
|
69
74
|
case 'qemu':
|
70
75
|
if (fieldset.toggle && fieldset.new_vm){
|
@@ -87,6 +92,7 @@ function toggleFieldset(fieldset, index, fieldsets){
|
|
87
92
|
server_input_hidden.attr('disabled','disabled');
|
88
93
|
break;
|
89
94
|
default:
|
95
|
+
console.log("unkown type="+fieldset.selected);
|
90
96
|
break;
|
91
97
|
}
|
92
98
|
}
|
@@ -41,75 +41,90 @@ function cdromSelected(item) {
|
|
41
41
|
return false;
|
42
42
|
}
|
43
43
|
|
44
|
-
function initCdromStorage(){
|
44
|
+
function initCdromStorage() {
|
45
45
|
var select = '#host_compute_attributes_config_attributes_cdrom_storage';
|
46
|
-
$(select + ' option:selected').prop('selected',false);
|
46
|
+
$(select + ' option:selected').prop('selected', false);
|
47
47
|
$(select).val('');
|
48
48
|
}
|
49
49
|
|
50
|
-
function initCdromOptions(name){
|
51
|
-
var select = '#host_compute_attributes_config_attributes_cdrom_'+name;
|
50
|
+
function initCdromOptions(name) {
|
51
|
+
var select = '#host_compute_attributes_config_attributes_cdrom_' + name;
|
52
52
|
$(select).empty();
|
53
53
|
$(select).append($("<option></option>").val('').text(''));
|
54
54
|
$(select).val('');
|
55
55
|
}
|
56
56
|
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
|
63
|
-
|
64
|
-
|
65
|
-
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
|
76
|
-
|
77
|
-
|
78
|
-
|
79
|
-
}
|
57
|
+
function storageIsoSelected(item) {
|
58
|
+
var storage = $(item).val();
|
59
|
+
if (storage != '') {
|
60
|
+
tfm.tools.showSpinner();
|
61
|
+
$.getJSON({
|
62
|
+
type: 'get',
|
63
|
+
url: '/foreman_fog_proxmox/isos/' + storage,
|
64
|
+
complete: function () {
|
65
|
+
tfm.tools.hideSpinner();
|
66
|
+
},
|
67
|
+
error: function (j, status, error) {
|
68
|
+
console.log("Error=" + error + ", status=" + status + " loading isos for storage=" + storage);
|
69
|
+
},
|
70
|
+
success: function (isos) {
|
71
|
+
initCdromOptions('iso');
|
72
|
+
$.each(isos, function (i, iso) {
|
73
|
+
$('#host_compute_attributes_config_attributes_cdrom_iso').append($("<option></option>").val(iso.volid).text(iso.volid));
|
74
|
+
});
|
75
|
+
}
|
76
|
+
});
|
77
|
+
} else {
|
78
|
+
initCdromOptions('iso');
|
80
79
|
}
|
80
|
+
}
|
81
81
|
|
82
|
-
function controllerSelected(item){
|
82
|
+
function controllerSelected(item) {
|
83
83
|
var controller = $(item).val();
|
84
|
-
var
|
85
|
-
var pattern = /(\w+)(\d+)(\w+)/i;
|
86
|
-
var index = pattern.exec(id)[2];
|
84
|
+
var index = getIndex(item);
|
87
85
|
var max = computeControllerMaxDevice(controller);
|
88
|
-
|
86
|
+
var device_selector = '#host_compute_attributes_volumes_attributes_' + index + '_device';
|
87
|
+
$(device_selector).attr('data-soft-max', max);
|
88
|
+
var device = $(device_selector).limitedSpinner('value');
|
89
|
+
$('#host_compute_attributes_volumes_attributes_' + index + '_id').val(controller + device);
|
89
90
|
tfm.numFields.initAll();
|
90
91
|
}
|
91
92
|
|
92
|
-
function
|
93
|
+
function deviceSelected(item) {
|
94
|
+
var device = $(item).limitedSpinner('value');
|
95
|
+
console.log("device=" + device);
|
96
|
+
var index = getIndex(item);
|
97
|
+
var controller_selector = '#host_compute_attributes_volumes_attributes_' + index + '_controller';
|
98
|
+
var controller = $(controller_selector).val();
|
99
|
+
$('#host_compute_attributes_volumes_attributes_' + index + '_id').val(controller + device);
|
100
|
+
tfm.numFields.initAll();
|
101
|
+
}
|
102
|
+
|
103
|
+
function getIndex(item) {
|
104
|
+
var id = $(item).attr('id');
|
105
|
+
var pattern = /(host_compute_attributes_volumes_attributes_)(\d+)[_](.*)/i;
|
106
|
+
pattern_a = pattern.exec(id);
|
107
|
+
var index = pattern_a[2];
|
108
|
+
console.log("index=" + index);
|
109
|
+
return index;
|
110
|
+
}
|
111
|
+
|
112
|
+
function computeControllerMaxDevice(controller) {
|
93
113
|
switch (controller) {
|
94
114
|
case 'ide':
|
95
115
|
return 3;
|
96
|
-
break;
|
97
116
|
case 'sata':
|
98
117
|
return 5;
|
99
|
-
break;
|
100
118
|
case 'scsi':
|
101
119
|
return 13;
|
102
|
-
break;
|
103
120
|
case 'virtio':
|
104
121
|
return 15;
|
105
|
-
break;
|
106
122
|
default:
|
107
123
|
return 1;
|
108
|
-
break;
|
109
124
|
}
|
110
125
|
}
|
111
126
|
|
112
|
-
function balloonSelected(item){
|
127
|
+
function balloonSelected(item) {
|
113
128
|
var ballooned = $(item).is(':checked');
|
114
129
|
var memory_f = $("input[name$='[config_attributes][memory]']:hidden");
|
115
130
|
var min_memory_f = $("input[id$='config_attributes_min_memory']");
|
@@ -120,13 +135,13 @@ function balloonSelected(item){
|
|
120
135
|
min_memory_f.removeAttr('disabled');
|
121
136
|
shares_f.removeAttr('disabled');
|
122
137
|
var max = memory_f.val();
|
123
|
-
console.log("max="+max);
|
124
|
-
min_memory_f.attr('data-soft-max',max);
|
138
|
+
console.log("max=" + max);
|
139
|
+
min_memory_f.attr('data-soft-max', max);
|
125
140
|
} else {
|
126
|
-
min_memory_f.attr('disabled','disabled');
|
127
|
-
min_memory_hidden_f.attr('value','');
|
128
|
-
shares_f.attr('disabled','disabled');
|
129
|
-
shares_hidden_f.attr('value','');
|
141
|
+
min_memory_f.attr('disabled', 'disabled');
|
142
|
+
min_memory_hidden_f.attr('value', '');
|
143
|
+
shares_f.attr('disabled', 'disabled');
|
144
|
+
shares_hidden_f.attr('value', '');
|
130
145
|
}
|
131
146
|
tfm.numFields.initAll();
|
132
147
|
}
|
@@ -96,9 +96,10 @@ module ProxmoxContainerHelper
|
|
96
96
|
def parse_container_volume(args)
|
97
97
|
disk = {}
|
98
98
|
id = args['id']
|
99
|
-
id = "mp#{args['device']}"
|
99
|
+
id = "mp#{args['device']}" if args.has_key?('device') && !id
|
100
100
|
delete = args['_delete'].to_i == 1
|
101
101
|
logger.debug("parse_container_volume() args=#{args}")
|
102
|
+
return args if ForemanFogProxmox::Value.empty?(id) || server_disk?(id)
|
102
103
|
args.delete_if { |_key,value| ForemanFogProxmox::Value.empty?(value) }
|
103
104
|
if delete
|
104
105
|
logger.debug("parse_container_volume(): delete id=#{id}")
|
@@ -46,22 +46,27 @@ end
|
|
46
46
|
pass = obj.attributes.has_key?(attr)
|
47
47
|
pass ? "********" : ''
|
48
48
|
end
|
49
|
+
|
50
|
+
def new_child_fields_template_typed(form_builder, association, options = { })
|
51
|
+
unless options[:object].present?
|
52
|
+
association_object = form_builder.object.class.reflect_on_association(association)
|
53
|
+
options[:object] = association_object.klass.new(association_object.foreign_key => form_builder.object.id)
|
54
|
+
end
|
55
|
+
options[:partial] ||= association.to_s.singularize
|
56
|
+
options[:form_builder_local] ||= :f
|
57
|
+
options[:form_builder_attrs] ||= {}
|
49
58
|
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
end
|
55
|
-
options[:partial] ||= association.to_s.singularize
|
56
|
-
options[:form_builder_local] ||= :f
|
57
|
-
options[:form_builder_attrs] ||= {}
|
58
|
-
|
59
|
-
content_tag(:div, :id => "#{options[:type]}_#{association}", :style => 'display: none') do
|
60
|
-
form_builder.fields_for(association, options[:object], :child_index => "0") do |f|
|
61
|
-
render(:partial => options[:partial], :layout => options[:layout],
|
62
|
-
:locals => { options[:form_builder_local] => f }.merge(options[:form_builder_attrs]))
|
63
|
-
end
|
59
|
+
content_tag(:div, :class => "#{options[:type]}_#{association}_fields_template form_template #{}", :style => "display: none;") do
|
60
|
+
form_builder.fields_for(association, options[:object], :child_index => "new_#{options[:type]}_#{association}") do |f|
|
61
|
+
render(:partial => options[:partial], :layout => options[:layout],
|
62
|
+
:locals => { options[:form_builder_local] => f }.merge(options[:form_builder_attrs]))
|
64
63
|
end
|
65
64
|
end
|
65
|
+
end
|
66
66
|
|
67
|
+
def add_child_link_typed(name, association, type, opts = {})
|
68
|
+
opts[:class] = [opts[:class], "add_nested_fields btn btn-primary"].compact.join(" ")
|
69
|
+
opts[:"data-association"] = (type + '_' + association.to_s).to_sym
|
70
|
+
link_to_function(name.to_s, "add_child_node(this);tfm.numFields.initAll();", opts)
|
71
|
+
end
|
67
72
|
end
|
@@ -103,8 +103,8 @@ module ProxmoxServerHelper
|
|
103
103
|
def parse_server_volume(args)
|
104
104
|
disk = {}
|
105
105
|
id = args['id']
|
106
|
-
id = "#{args['controller']}#{args['device']}"
|
107
|
-
return args if ForemanFogProxmox::Value.empty?(id)
|
106
|
+
id = "#{args['controller']}#{args['device']}" if args.has_key?('controller') && args.has_key?('device') && !id
|
107
|
+
return args if ForemanFogProxmox::Value.empty?(id) || id == 'rootfs'
|
108
108
|
delete = args['_delete'].to_i == 1
|
109
109
|
args.delete_if { |_key,value| ForemanFogProxmox::Value.empty?(value) }
|
110
110
|
if delete
|
@@ -113,9 +113,9 @@ module ProxmoxServerHelper
|
|
113
113
|
disk
|
114
114
|
else
|
115
115
|
disk.store(:id, id)
|
116
|
-
disk.store(:volid, args['volid'])
|
117
|
-
disk.store(:storage, args['storage'].to_s)
|
118
|
-
disk.store(:size, args['size'].to_i)
|
116
|
+
disk.store(:volid, args['volid']) if args.has_key?('volid')
|
117
|
+
disk.store(:storage, args['storage'].to_s) if args.has_key?('storage')
|
118
|
+
disk.store(:size, args['size'].to_i) if args.has_key?('size')
|
119
119
|
options = args.reject { |key,_value| %w[id volid controller device storage size _delete].include? key}
|
120
120
|
disk.store(:options, options)
|
121
121
|
logger.debug("parse_server_volume(): add disk=#{disk}")
|
@@ -70,6 +70,10 @@ module ProxmoxVmHelper
|
|
70
70
|
args['volumes_attributes'].each_value { |value| value['size'] = (value['size'].to_i / GIGA).to_s unless ForemanFogProxmox::Value.empty?(value['size']) }
|
71
71
|
end
|
72
72
|
|
73
|
+
def remove_deletes(args)
|
74
|
+
args['volumes_attributes'].delete_if { |_key,value| value.has_key? '_delete' }
|
75
|
+
end
|
76
|
+
|
73
77
|
def convert_memory_size(config_hash, key)
|
74
78
|
config_hash.store(key, (config_hash[key].to_i / MEGA).to_s) unless ForemanFogProxmox::Value.empty?(config_hash[key])
|
75
79
|
end
|
@@ -83,4 +87,12 @@ module ProxmoxVmHelper
|
|
83
87
|
return type, vmid
|
84
88
|
end
|
85
89
|
|
90
|
+
def mount_point_disk?(id)
|
91
|
+
/^(mp)(\d+)$/.match?(id)
|
92
|
+
end
|
93
|
+
|
94
|
+
def server_disk?(id)
|
95
|
+
/^(scsi|sata|virtio|ide)(\d+)$/.match?(id)
|
96
|
+
end
|
97
|
+
|
86
98
|
end
|
@@ -120,8 +120,13 @@ module ForemanFogProxmox
|
|
120
120
|
|
121
121
|
def host_interfaces_attrs(host)
|
122
122
|
host.interfaces.select(&:physical?).each.with_index.reduce({}) do |hash, (nic, index)|
|
123
|
-
|
123
|
+
# Set default interface identifier to net[n]
|
124
|
+
nic.identifier = "net%{index}" % {index: index} if nic.identifier.empty?
|
124
125
|
raise ::Foreman::Exception.new _("Invalid identifier interface[%{index}]. Must be net[n] with n integer >= 0" % { index: index }) unless Fog::Proxmox::NicHelper.valid?(nic.identifier)
|
126
|
+
# Set default container interface name to eth[n]
|
127
|
+
container = host.compute_attributes['type'] == 'lxc'
|
128
|
+
nic.compute_attributes['name'] = "eth%{index}" % {index: index} if container && nic.compute_attributes['name'].empty?
|
129
|
+
raise ::Foreman::Exception.new _("Invalid name interface[%{index}]. Must be eth[n] with n integer >= 0" % { index: index }) if container && !/^(eth)(\d+)$/.match?(nic.compute_attributes['name'])
|
125
130
|
nic_compute_attributes = nic.compute_attributes.merge(id: nic.identifier)
|
126
131
|
nic_compute_attributes.store(:ip, nic.ip) if (nic.ip && !nic.ip.empty?)
|
127
132
|
nic_compute_attributes.store(:ip6, nic.ip6) if (nic.ip6 && !nic.ip6.empty?)
|
@@ -232,6 +237,7 @@ module ForemanFogProxmox
|
|
232
237
|
else
|
233
238
|
logger.debug(_("create_vm(): %{args}") % { args: args })
|
234
239
|
convert_sizes(args)
|
240
|
+
remove_deletes(args)
|
235
241
|
case type
|
236
242
|
when 'qemu'
|
237
243
|
node.servers.create(parse_server_vm(args))
|
@@ -422,7 +428,7 @@ module ForemanFogProxmox
|
|
422
428
|
cpu: 'kvm64',
|
423
429
|
scsihw: 'virtio-scsi-pci',
|
424
430
|
ide2: "none,media=cdrom",
|
425
|
-
templated: 0).merge(Fog::Proxmox::DiskHelper.flatten(volume_server_defaults)).merge(Fog::Proxmox::NicHelper.flatten(interface_server_defaults))
|
431
|
+
templated: 0).merge(Fog::Proxmox::DiskHelper.flatten(volume_server_defaults)).merge(Fog::Proxmox::DiskHelper.flatten(volume_container_defaults)).merge(Fog::Proxmox::NicHelper.flatten(interface_server_defaults))
|
426
432
|
end
|
427
433
|
|
428
434
|
def vm_container_instance_defaults
|
@@ -432,7 +438,7 @@ module ForemanFogProxmox
|
|
432
438
|
type: 'lxc',
|
433
439
|
node: node.to_s,
|
434
440
|
memory: 512 * MEGA,
|
435
|
-
templated: 0).merge(Fog::Proxmox::DiskHelper.flatten(volume_container_defaults)).merge(Fog::Proxmox::NicHelper.container_flatten(interface_container_defaults))
|
441
|
+
templated: 0).merge(Fog::Proxmox::DiskHelper.flatten(volume_server_defaults)).merge(Fog::Proxmox::DiskHelper.flatten(volume_container_defaults)).merge(Fog::Proxmox::NicHelper.container_flatten(interface_container_defaults))
|
436
442
|
end
|
437
443
|
|
438
444
|
def vm_instance_defaults
|
@@ -20,53 +20,40 @@ along with ForemanFogProxmox. If not, see <http://www.gnu.org/licenses/>. %>
|
|
20
20
|
<% server = type == 'qemu' %>
|
21
21
|
<% container = type == 'lxc' %>
|
22
22
|
|
23
|
-
<%=
|
23
|
+
<%= new_child_fields_template_typed(f, :volumes, {
|
24
|
+
:type => 'server',
|
24
25
|
:object => compute_resource.new_volume_server,
|
25
26
|
:partial => provider_partial(compute_resource, 'server/volume'),
|
26
27
|
:form_builder_attrs => { :type => type, :compute_resource => compute_resource, :new_host => new_vm, :new_vm => new_vm, :remove_title => _('remove storage volume') },
|
27
28
|
:layout => "compute_resources_vms/form/#{item_layout}_layout" }) %>
|
28
|
-
<%=
|
29
|
+
<%= new_child_fields_template_typed(f, :volumes, {
|
30
|
+
:type => 'container',
|
29
31
|
:object => compute_resource.new_volume_container(id: 'mp0'),
|
30
32
|
:partial => provider_partial(compute_resource, 'container/volume_mp'),
|
31
33
|
:form_builder_attrs => { :type => type, :compute_resource => compute_resource, :new_host => new_vm, :new_vm => new_vm, :remove_title => _('remove storage volume') },
|
32
34
|
:layout => "compute_resources_vms/form/#{item_layout}_layout" }) %>
|
33
35
|
|
34
36
|
|
35
|
-
|
36
|
-
<div id="server_volumes">
|
37
|
-
<%= f.fields_for :volumes do |i| %>
|
38
|
-
<%= render :partial => provider_partial(compute_resource, 'server/volume'), :locals => { :f => i, :type => type, :compute_resource => compute_resource, :new_host => new_vm, :new_vm => new_vm, :remove_title => _('remove storage volume') }, :layout => "compute_resources_vms/form/#{item_layout}_layout" %>
|
39
|
-
<% end %>
|
40
|
-
</div>
|
41
|
-
<%= second_child_fields_template(f, :volumes, {
|
42
|
-
:object => compute_resource.new_volume_container(id: 'rootfs'),
|
43
|
-
:partial => provider_partial(compute_resource, 'container/volume_rootfs'),
|
44
|
-
:type => 'container',
|
45
|
-
:form_builder_attrs => { :type => type, :compute_resource => compute_resource, :new_host => new_vm, :new_vm => new_vm, :remove_title => _('remove storage volume') },
|
46
|
-
:layout => "compute_resources_vms/form/#{item_layout}_layout" }) %>
|
47
|
-
<% end %>
|
48
|
-
<% if container %>
|
49
|
-
<div id="container_volumes">
|
37
|
+
|
50
38
|
<%= f.fields_for :volumes do |i| %>
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
|
63
|
-
|
64
|
-
<% end %>
|
65
|
-
|
66
|
-
<%= add_child_link '+ ' + _("Add Volume"), :server_volumes, { :class => "info", :style => ("display: none;" unless server), :title => _('add new storage volume') } %>
|
67
|
-
<% end %>
|
39
|
+
<% if i.object.id == 'rootfs' %>
|
40
|
+
<div id="container_volumes_rootfs" style="<%= 'display: ' + (container ? 'block' : 'none') + ';' %>">
|
41
|
+
<%= render :partial => provider_partial(compute_resource, 'container/volume_rootfs'), :locals => { :f => i, :type => type, :compute_resource => compute_resource, :new_host => new_vm, :new_vm => new_vm, :remove_title => _('remove storage volume'), :disabled => !container }, :layout => "compute_resources_vms/form/#{item_layout}_layout" %>
|
42
|
+
</div>
|
43
|
+
<% elsif mount_point_disk?(i.object.id) %>
|
44
|
+
<div id="container_volumes_mp" style="<%= 'display: ' + (container ? 'block' : 'none') + ';' %>">
|
45
|
+
<%= render :partial => provider_partial(compute_resource, 'container/volume_mp'), :locals => { :f => i, :type => type, :compute_resource => compute_resource, :new_host => new_vm, :new_vm => new_vm, :remove_title => _('remove storage volume'), :disabled => !container }, :layout => "compute_resources_vms/form/#{item_layout}_layout" %>
|
46
|
+
</div>
|
47
|
+
<% elsif server_disk?(i.object.id) %>
|
48
|
+
<div id="server_volumes" style="<%= 'display: ' + (server ? 'block' : 'none') + ';' %>">
|
49
|
+
<%= render :partial => provider_partial(compute_resource, 'server/volume'), :locals => { :f => i, :type => type, :compute_resource => compute_resource, :new_host => new_vm, :new_vm => new_vm, :remove_title => _('remove storage volume'), :disabled => !server }, :layout => "compute_resources_vms/form/#{item_layout}_layout" %>
|
50
|
+
</div>
|
51
|
+
<% end %>
|
52
|
+
<% end %>
|
53
|
+
|
68
54
|
<% if new_vm %>
|
69
|
-
<%=
|
55
|
+
<%= add_child_link_typed '+ ' + _("Add Volume"), :volumes, 'server', { :class => "info #{'hide' unless server}", :title => _('add new storage volume') } %>
|
56
|
+
<%= add_child_link_typed '+ ' + _("Add Volume"), :volumes, 'container', { :class => "info #{'hide' unless container}", :title => _('add new storage volume') } %>
|
70
57
|
<% end %>
|
71
58
|
|
72
59
|
|
@@ -20,6 +20,7 @@ along with ForemanFogProxmox. If not, see <http://www.gnu.org/licenses/>. %>
|
|
20
20
|
<%= field_set_tag _("Mount point"), :id => "container_volume_#{f.index}", :class => ('hide' unless container), :disabled => !container do %>
|
21
21
|
<%= f.hidden_field :volid if !new_vm %>
|
22
22
|
<%= select_f f, :storage, compute_resource.storages, :storage, :storage, { }, :label => _('Storage'), :label_size => "col-md-2", :disabled => !new_vm %>
|
23
|
+
<%= text_f f, :mp, :label => _('Mount point'), :label_size => "col-md-2", :disabled => !new_vm, :required => true %>
|
23
24
|
<%= counter_f f, :device, :label => _('Device'), :label_size => "col-md-2", :class => ('hide' if f.object.rootfs?), :disabled => (!new_vm || f.object.rootfs?), :'data-soft-max' => 10 %>
|
24
25
|
<%= byte_size_f f, :size, :class => "input-mini", :label => _("Size"), :label_size => "col-md-2", :disabled => !new_vm %>
|
25
26
|
<% end %>
|
@@ -16,6 +16,7 @@ You should have received a copy of the GNU General Public License
|
|
16
16
|
along with ForemanFogProxmox. If not, see <http://www.gnu.org/licenses/>. %>
|
17
17
|
|
18
18
|
<%= javascript_include_tag 'foreman_fog_proxmox/proxmox_vm_server', "data-turbolinks-track" => true %>
|
19
|
+
|
19
20
|
<% server = type == 'qemu' %>
|
20
21
|
|
21
22
|
<%= field_set_tag n_("Main option", "Main options", 2), :id => "server_config_options", :class => 'hide', :disabled => !server do %>
|
@@ -21,7 +21,7 @@ along with ForemanFogProxmox. If not, see <http://www.gnu.org/licenses/>. %>
|
|
21
21
|
<%= f.hidden_field :volid if !new_vm %>
|
22
22
|
<%= select_f f, :storage, compute_resource.storages, :storage, :storage, { }, :label => _('Storage'), :label_size => "col-md-2", :disabled => !new_vm %>
|
23
23
|
<%= select_f f, :controller, proxmox_controllers_map, :id, :name, { }, :label => _('Controller'), :label_size => "col-md-2", :disabled => !new_vm, :onchange => 'controllerSelected(this)' %>
|
24
|
-
<%= counter_f f, :device, :label => _('Device'), :label_size => "col-md-2", :disabled => !new_vm, :'data-soft-max' => proxmox_max_device(f.object.controller) %>
|
24
|
+
<%= counter_f f, :device, :label => _('Device'), :label_size => "col-md-2", :disabled => !new_vm, :'data-soft-max' => proxmox_max_device(f.object.controller), :onchange => 'deviceSelected(this)' %>
|
25
25
|
<%= select_f f, :cache, proxmox_caches_map, :id, :name, { }, :label => _('Cache'), :label_size => "col-md-2" %>
|
26
26
|
<%= byte_size_f f, :size, :class => "input-mini", :label => _("Size"), :label_size => "col-md-2", :disabled => !new_vm %>
|
27
27
|
<% end %>
|
@@ -45,7 +45,8 @@ class ProxmoxServerHelperTest < ActiveSupport::TestCase
|
|
45
45
|
'sockets' => '1'
|
46
46
|
},
|
47
47
|
'volumes_attributes' => {
|
48
|
-
'0'=> { 'controller' => 'scsi', 'device' => '0', 'storage' => 'local-lvm', 'size' => '1073741824', 'cache' => 'none' }
|
48
|
+
'0'=> { 'controller' => 'scsi', 'device' => '0', 'storage' => 'local-lvm', 'size' => '1073741824', 'cache' => 'none' },
|
49
|
+
'1'=> { 'controller' => 'virtio', 'device' => '0', 'storage' => 'local-lvm', 'size' => '1073741824', 'cache' => 'none' }
|
49
50
|
},
|
50
51
|
'interfaces_attributes' => {
|
51
52
|
'0' => { 'id' => 'net0', 'model' => 'virtio', 'bridge' => 'vmbr0', 'firewall' => '0', 'link_down' => '0', 'rate' => nil },
|
@@ -92,10 +93,20 @@ class ProxmoxServerHelperTest < ActiveSupport::TestCase
|
|
92
93
|
test '#volume with scsi 1Gb' do
|
93
94
|
volumes = parse_server_volumes(host['volumes_attributes'])
|
94
95
|
assert !volumes.empty?
|
96
|
+
assert volumes.size, 2
|
95
97
|
assert volume = volumes.first
|
96
98
|
assert volume.has_key?(:scsi0)
|
97
99
|
assert_equal 'local-lvm:1073741824,cache=none', volume[:scsi0]
|
98
100
|
end
|
101
|
+
|
102
|
+
test '#volume with virtio 1Gb' do
|
103
|
+
volumes = parse_server_volumes(host['volumes_attributes'])
|
104
|
+
assert !volumes.empty?
|
105
|
+
assert volumes.size, 2
|
106
|
+
assert volume = volumes[1]
|
107
|
+
assert volume.has_key?(:virtio0)
|
108
|
+
assert_equal 'local-lvm:1073741824,cache=none', volume[:virtio0]
|
109
|
+
end
|
99
110
|
|
100
111
|
test '#volume delete scsi0' do
|
101
112
|
volumes = parse_server_volumes(host_delete['volumes_attributes'])
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: foreman_fog_proxmox
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.5.
|
4
|
+
version: 0.5.5
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Tristan Robert
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2018-11-
|
11
|
+
date: 2018-11-27 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: fog-proxmox
|
@@ -189,11 +189,11 @@ signing_key:
|
|
189
189
|
specification_version: 4
|
190
190
|
summary: Foreman plugin that adds Proxmox VE compute resource using fog-proxmox
|
191
191
|
test_files:
|
192
|
-
- test/functional/compute_resources_controller_test.rb
|
193
|
-
- test/factories/proxmox_factory.rb
|
194
192
|
- test/unit/foreman_fog_proxmox/proxmox_test_helpers.rb
|
195
|
-
- test/unit/foreman_fog_proxmox/
|
193
|
+
- test/unit/foreman_fog_proxmox/helpers/proxmox_vm_helper_test.rb
|
196
194
|
- test/unit/foreman_fog_proxmox/helpers/proxmox_container_helper_test.rb
|
197
195
|
- test/unit/foreman_fog_proxmox/helpers/proxmox_server_helper_test.rb
|
198
|
-
- test/unit/foreman_fog_proxmox/
|
196
|
+
- test/unit/foreman_fog_proxmox/proxmox_test.rb
|
197
|
+
- test/factories/proxmox_factory.rb
|
198
|
+
- test/functional/compute_resources_controller_test.rb
|
199
199
|
- test/test_plugin_helper.rb
|