]> git.proxmox.com Git - pve-manager.git/blame - PVE/API2/ReplicationConfig.pm
Fix #1372: require manually entering the Ceph Pool id before destroying a pool
[pve-manager.git] / PVE / API2 / ReplicationConfig.pm
CommitLineData
892821fd
DM
1package PVE::API2::ReplicationConfig;
2
3use warnings;
4use strict;
5
6use PVE::Tools qw(extract_param);
f9d38c54 7use PVE::Exception qw(raise_perm_exc raise_param_exc);
892821fd
DM
8use PVE::JSONSchema qw(get_standard_option);
9use PVE::RPCEnvironment;
10use PVE::ReplicationConfig;
4542a42a 11use PVE::Cluster;
892821fd
DM
12
13use PVE::RESTHandler;
14
15use base qw(PVE::RESTHandler);
16
17__PACKAGE__->register_method ({
18 name => 'index',
19 path => '',
20 method => 'GET',
21 description => "List replication jobs.",
22 permissions => {
23 description => "Requires the VM.Audit permission on /vms/<vmid>.",
24 user => 'all',
25 },
26 parameters => {
27 additionalProperties => 0,
28 properties => {},
29 },
30 returns => {
31 type => 'array',
32 items => {
33 type => "object",
34 properties => {},
35 },
4b48563a 36 links => [ { rel => 'child', href => "{id}" } ],
892821fd
DM
37 },
38 code => sub {
39 my ($param) = @_;
40
41 my $rpcenv = PVE::RPCEnvironment::get();
42 my $authuser = $rpcenv->get_user();
43
44 my $cfg = PVE::ReplicationConfig->new();
45
46 my $res = [];
47 foreach my $id (sort keys %{$cfg->{ids}}) {
48 my $d = $cfg->{ids}->{$id};
49 my $vmid = $d->{guest};
50 next if !$rpcenv->check($authuser, "/vms/$vmid", [ 'VM.Audit' ]);
51 $d->{id} = $id;
52 push @$res, $d;
53 }
54
55 return $res;
56 }});
57
58__PACKAGE__->register_method ({
59 name => 'read',
60 path => '{id}',
61 method => 'GET',
62 description => "Read replication job configuration.",
63 permissions => {
64 description => "Requires the VM.Audit permission on /vms/<vmid>.",
65 user => 'all',
66 },
67 parameters => {
68 additionalProperties => 0,
69 properties => {
70 id => get_standard_option('pve-replication-id'),
71 },
72 },
73 returns => { type => 'object' },
74 code => sub {
75 my ($param) = @_;
76
77 my $rpcenv = PVE::RPCEnvironment::get();
78 my $authuser = $rpcenv->get_user();
79
80 my $cfg = PVE::ReplicationConfig->new();
81
82 my $data = $cfg->{ids}->{$param->{id}};
83
84 die "no such replication job '$param->{id}'\n" if !defined($data);
85
86 my $vmid = $data->{guest};
87
88 raise_perm_exc() if !$rpcenv->check($authuser, "/vms/$vmid", [ 'VM.Audit' ]);
89
90 $data->{id} = $param->{id};
91
a4dc8611
DC
92 $data->{digest} = $cfg->{digest};
93
892821fd
DM
94 return $data;
95 }});
96
97__PACKAGE__->register_method ({
98 name => 'create',
99 path => '',
100 protected => 1,
101 method => 'POST',
102 description => "Create a new replication job",
103 permissions => {
104 check => ['perm', '/storage', ['Datastore.Allocate']],
105 },
106 parameters => PVE::ReplicationConfig->createSchema(),
107 returns => { type => 'null' },
108 code => sub {
109 my ($param) = @_;
110
111 my $type = extract_param($param, 'type');
112 my $plugin = PVE::ReplicationConfig->lookup($type);
113 my $id = extract_param($param, 'id');
114
a9da300d
DM
115 # extract guest ID from job ID
116 my ($guest) = PVE::ReplicationConfig::parse_replication_job_id($id);
117
4542a42a
DM
118 my $nodelist = PVE::Cluster::get_members();
119 my $vmlist = PVE::Cluster::get_vmlist();
120
121 die "Guest '$guest' does not exists.\n"
122 if !defined($vmlist->{ids}->{$guest});
123 die "Target '$param->{target}' does not exists.\n"
124 if defined($param->{target}) && !defined($nodelist->{$param->{target}});
125
892821fd
DM
126 my $code = sub {
127 my $cfg = PVE::ReplicationConfig->new();
128
892821fd
DM
129 die "replication job '$id' already exists\n"
130 if $cfg->{ids}->{$id};
131
132 my $opts = $plugin->check_config($id, $param, 1, 1);
133
a9da300d
DM
134 $opts->{guest} = $guest;
135
892821fd
DM
136 $cfg->{ids}->{$id} = $opts;
137
138 $cfg->write();
139 };
140
141 PVE::ReplicationConfig::lock($code);
142
143 return undef;
144 }});
145
146
147__PACKAGE__->register_method ({
148 name => 'update',
149 protected => 1,
150 path => '{id}',
151 method => 'PUT',
152 description => "Update replication job configuration.",
153 permissions => {
154 check => ['perm', '/storage', ['Datastore.Allocate']],
155 },
156 parameters => PVE::ReplicationConfig->updateSchema(),
157 returns => { type => 'null' },
158 code => sub {
159 my ($param) = @_;
160
161 my $id = extract_param($param, 'id');
a4dc8611 162 my $digest = extract_param($param, 'digest');
892821fd
DM
163
164 my $code = sub {
165 my $cfg = PVE::ReplicationConfig->new();
166
a4dc8611
DC
167 PVE::SectionConfig::assert_if_modified($cfg, $digest);
168
892821fd
DM
169 my $data = $cfg->{ids}->{$id};
170 die "no such job '$id'\n" if !$data;
171
172 my $plugin = PVE::ReplicationConfig->lookup($data->{type});
173 my $opts = $plugin->check_config($id, $param, 0, 1);
174
175 foreach my $k (%$opts) {
176 $data->{$k} = $opts->{$k};
177 }
178
179 $cfg->write();
180 };
181
182 PVE::ReplicationConfig::lock($code);
183
184 return undef;
185 }});
186
187__PACKAGE__->register_method ({
188 name => 'delete',
189 protected => 1,
190 path => '{id}',
191 method => 'DELETE',
f9d38c54 192 description => "Mark replication job for removal.",
892821fd
DM
193 permissions => {
194 check => ['perm', '/storage', ['Datastore.Allocate']],
195 },
196 parameters => {
197 additionalProperties => 0,
198 properties => {
199 id => get_standard_option('pve-replication-id'),
200 keep => {
201 description => "Keep replicated data at target (do not remove).",
202 type => 'boolean',
203 optional => 1,
204 default => 0,
205 },
948136a4
WL
206 force => {
207 description => "Will remove the jobconfig entry, but will not cleanup.",
208 type => 'boolean',
209 optional => 1,
210 default => 0,
211 },
892821fd
DM
212 }
213 },
214 returns => { type => 'null' },
215 code => sub {
216 my ($param) = @_;
217
bc1ec7bc
DM
218 my $rpcenv = PVE::RPCEnvironment::get();
219
892821fd
DM
220 my $code = sub {
221 my $cfg = PVE::ReplicationConfig->new();
222
f9d38c54 223 my $id = $param->{id};
948136a4 224 if ($param->{force}) {
9a427c6c 225 raise_param_exc({ 'keep' => "conflicts with parameter 'force'" }) if $param->{keep};
948136a4 226 delete $cfg->{ids}->{$id};
f9d38c54 227 } else {
948136a4
WL
228 my $jobcfg = $cfg->{ids}->{$id};
229 die "no such job '$id'\n" if !$jobcfg;
230
231 if (!$param->{keep} && $jobcfg->{type} eq 'local') {
232 # remove local snapshots and remote volumes
233 $jobcfg->{remove_job} = 'full';
234 } else {
235 # only remove local snapshots
236 $jobcfg->{remove_job} = 'local';
237 }
238
239 warn "Replication job removal is a background task and will take some time.\n"
240 if $rpcenv->{type} eq 'cli';
892821fd 241 }
892821fd
DM
242 $cfg->write();
243 };
244
245 PVE::ReplicationConfig::lock($code);
246
247 return undef;
248 }});
f9d38c54 249
892821fd 2501;