]> git.proxmox.com Git - pve-container.git/blame - src/PVE/API2/LXC/Config.pm
fixup: slight code cleanup
[pve-container.git] / src / PVE / API2 / LXC / Config.pm
CommitLineData
52389a07
DM
1package PVE::API2::LXC::Config;
2
3use strict;
4use warnings;
5
6use PVE::SafeSyslog;
7use PVE::Tools qw(extract_param run_command);
8use PVE::Exception qw(raise raise_param_exc);
9use PVE::INotify;
10use PVE::Cluster qw(cfs_read_file);
11use PVE::AccessControl;
12use PVE::Firewall;
13use PVE::Storage;
14use PVE::RESTHandler;
15use PVE::RPCEnvironment;
16use PVE::LXC;
7c92bb72 17use PVE::LXC::Config;
52389a07 18use PVE::LXC::Create;
52389a07
DM
19use PVE::JSONSchema qw(get_standard_option);
20use base qw(PVE::RESTHandler);
21
22use Data::Dumper; # fixme: remove
23
24__PACKAGE__->register_method({
25 name => 'vm_config',
26 path => '',
27 method => 'GET',
28 proxyto => 'node',
29 description => "Get container configuration.",
30 permissions => {
31 check => ['perm', '/vms/{vmid}', [ 'VM.Audit' ]],
32 },
33 parameters => {
34 additionalProperties => 0,
35 properties => {
36 node => get_standard_option('pve-node'),
68e8f3c5 37 vmid => get_standard_option('pve-vmid', { completion => \&PVE::LXC::complete_ctid }),
98f59049
TL
38 snapshot => get_standard_option('pve-snapshot-name', {
39 description => "Fetch config values from given snapshot.",
40 optional => 1,
41 completion => sub {
42 my ($cmd, $pname, $cur, $args) = @_;
43 PVE::LXC::Config->snapshot_list($args->[0]);
44 },
45 }),
52389a07
DM
46 },
47 },
48 returns => {
49 type => "object",
7c92bb72
DM
50 properties => PVE::LXC::Config->json_config_properties({
51 lxc => {
52 description => "Array of lxc low-level configurations ([[key1, value1], [key2, value2] ...]).",
53 type => 'array',
54 items => { type => 'array', items => { type => 'string' }},
55 optional => 1,
56 },
52389a07
DM
57 digest => {
58 type => 'string',
59 description => 'SHA1 digest of configuration file. This can be used to prevent concurrent modifications.',
60 }
7c92bb72 61 }),
52389a07
DM
62 },
63 code => sub {
64 my ($param) = @_;
65
67afe46e 66 my $conf = PVE::LXC::Config->load_config($param->{vmid});
52389a07 67
b7d72f30 68 if (my $snapname = $param->{snapshot}) {
0a507a2d 69 my $snapshot = $conf->{snapshots}->{$snapname};
b7d72f30 70 die "snapshot '$snapname' does not exist\n" if !defined($snapshot);
0a507a2d
RV
71
72 # we need the digest of the file
73 $snapshot->{digest} = $conf->{digest};
74 $conf = $snapshot;
75 }
76
52389a07 77 delete $conf->{snapshots};
52389a07
DM
78
79 return $conf;
80 }});
81
82my $vm_config_perm_list = [
83 'VM.Config.Disk',
84 'VM.Config.CPU',
85 'VM.Config.Memory',
86 'VM.Config.Network',
87 'VM.Config.Options',
88 ];
89
90__PACKAGE__->register_method({
91 name => 'update_vm',
92 path => '',
93 method => 'PUT',
94 protected => 1,
95 proxyto => 'node',
96 description => "Set container options.",
97 permissions => {
98 check => ['perm', '/vms/{vmid}', $vm_config_perm_list, any => 1],
9d294016 99 description => 'non-volume mount points in rootfs and mp[n] are restricted to root@pam',
52389a07
DM
100 },
101 parameters => {
102 additionalProperties => 0,
1b4cf758 103 properties => PVE::LXC::Config->json_config_properties(
52389a07
DM
104 {
105 node => get_standard_option('pve-node'),
68e8f3c5 106 vmid => get_standard_option('pve-vmid', { completion => \&PVE::LXC::complete_ctid }),
52389a07
DM
107 delete => {
108 type => 'string', format => 'pve-configid-list',
109 description => "A list of settings you want to delete.",
110 optional => 1,
111 },
112 digest => {
113 type => 'string',
114 description => 'Prevent changes if current configuration file has different SHA1 digest. This can be used to prevent concurrent modifications.',
115 maxLength => 40,
116 optional => 1,
117 }
118 }),
119 },
120 returns => { type => 'null'},
121 code => sub {
122 my ($param) = @_;
123
124 my $rpcenv = PVE::RPCEnvironment::get();
125
126 my $authuser = $rpcenv->get_user();
127
128 my $node = extract_param($param, 'node');
129
130 my $vmid = extract_param($param, 'vmid');
131
132 my $digest = extract_param($param, 'digest');
133
134 die "no options specified\n" if !scalar(keys %$param);
135
136 my $delete_str = extract_param($param, 'delete');
137 my @delete = PVE::Tools::split_list($delete_str);
138
f1ba1a4b 139 PVE::LXC::check_ct_modify_config_perm($rpcenv, $authuser, $vmid, undef, {}, [@delete]);
52389a07
DM
140
141 foreach my $opt (@delete) {
142 raise_param_exc({ delete => "you can't use '-$opt' and " .
143 "-delete $opt' at the same time" })
144 if defined($param->{$opt});
145
1b4cf758 146 if (!PVE::LXC::Config->option_exists($opt)) {
52389a07
DM
147 raise_param_exc({ delete => "unknown option '$opt'" });
148 }
149 }
150
f1ba1a4b 151 PVE::LXC::check_ct_modify_config_perm($rpcenv, $authuser, $vmid, undef, $param, []);
52389a07
DM
152
153 my $storage_cfg = cfs_read_file("storage.cfg");
154
2aee38e5
WB
155 my $repl_conf = PVE::ReplicationConfig->new();
156 my $is_replicated = $repl_conf->check_for_existing_jobs($vmid, 1);
157 if ($is_replicated) {
158 PVE::LXC::Config->foreach_mountpoint_full($param, 0, sub {
159 my ($opt, $mountpoint) = @_;
160 my $volid = $mountpoint->{volume};
161 return if !$volid || !($mountpoint->{replicate}//1);
162 if ($mountpoint->{type} eq 'volume') {
163 my ($storeid, $format);
164 if ($volid =~ $PVE::LXC::NEW_DISK_RE) {
165 $storeid = $1;
166 $format = $mountpoint->{format} || PVE::Storage::storage_default_format($storage_cfg, $storeid);
167 } else {
168 ($storeid, undef) = PVE::Storage::parse_volume_id($volid, 1);
169 $format = (PVE::Storage::parse_volname($storage_cfg, $volid))[6];
170 }
171 return if PVE::Storage::storage_can_replicate($storage_cfg, $storeid, $format);
03b3e188
WB
172 my $scfg = PVE::Storage::storage_config($storage_cfg, $storeid);
173 return if $scfg->{shared};
2aee38e5
WB
174 }
175 die "cannot add non-replicatable volume to a replicated VM\n";
176 });
177 }
178
52389a07
DM
179 my $code = sub {
180
67afe46e
FG
181 my $conf = PVE::LXC::Config->load_config($vmid);
182 PVE::LXC::Config->check_lock($conf);
52389a07
DM
183
184 PVE::Tools::assert_if_modified($digest, $conf->{digest});
185
186 my $running = PVE::LXC::check_running($vmid);
187
1b4cf758 188 PVE::LXC::Config->update_pct_config($vmid, $conf, $running, $param, \@delete);
52389a07 189
67afe46e 190 PVE::LXC::Config->write_config($vmid, $conf);
f91f3669 191 PVE::LXC::update_lxc_config($vmid, $conf);
52389a07
DM
192 };
193
67afe46e 194 PVE::LXC::Config->lock_config($vmid, $code);
52389a07
DM
195
196 return undef;
197 }});
198
1991;