]>
Commit | Line | Data |
---|---|---|
c3346bf1 DM |
1 | package PMG::API2::Fetchmail; |
2 | ||
3 | use strict; | |
4 | use warnings; | |
5 | use Data::Dumper; | |
6eedc769 | 6 | use Clone 'clone'; |
c3346bf1 DM |
7 | |
8 | use PVE::SafeSyslog; | |
9 | use PVE::Tools qw(extract_param); | |
10 | use PVE::JSONSchema qw(get_standard_option); | |
11 | use PVE::RESTHandler; | |
12 | use PVE::INotify; | |
13 | ||
14 | use PMG::Config; | |
15 | use PMG::Fetchmail; | |
16 | ||
17 | use base qw(PVE::RESTHandler); | |
18 | ||
a81ce1a5 DM |
19 | my $fetchmail_properties = { |
20 | id => { | |
21 | description => "Unique ID", | |
22 | type => 'string', | |
23 | pattern => '[A-Za-z0-9]+', | |
24 | maxLength => 16, | |
25 | }, | |
26 | enable => { | |
27 | description => "Flag to enable or disable polling.", | |
28 | type => 'boolean', | |
29 | default => 0, | |
30 | optional => 1, | |
31 | }, | |
32 | server => { | |
33 | description => "Server address (IP or DNS name).", | |
34 | type => 'string', format => 'address', | |
35 | optional => 1, | |
36 | }, | |
37 | protocol => { | |
38 | description => "Specify the protocol to use when communicating with the remote mailserver", | |
39 | type => 'string', | |
40 | enum => [ 'pop3', 'imap' ], | |
41 | optional => 1, | |
42 | }, | |
43 | port => { | |
44 | description => "Port number.", | |
45 | type => 'integer', | |
46 | minimum => 1, | |
47 | maximum => 65535, | |
48 | optional => 1, | |
49 | }, | |
50 | interval => { | |
51 | description => "Only check this site every <interval> poll cycles. A poll cycle is 5 minutes.", | |
52 | type => 'integer', | |
53 | minimum => 1, | |
54 | maximum => 24*12*7, | |
55 | optional => 1, | |
56 | }, | |
57 | ssl => { | |
58 | description => "Use SSL.", | |
59 | type => 'boolean', | |
60 | optional => 1, | |
61 | default => 0, | |
62 | }, | |
63 | keep => { | |
64 | description => "Keep retrieved messages on the remote mailserver.", | |
65 | type => 'boolean', | |
66 | optional => 1, | |
67 | default => 0, | |
68 | }, | |
69 | user => { | |
70 | description => "The user identification to be used when logging in to the server", | |
71 | type => 'string', | |
72 | minLength => 1, | |
73 | maxLength => 64, | |
74 | optional => 1, | |
75 | }, | |
76 | pass => { | |
77 | description => "The password used tfor server login.", | |
78 | type => 'string', | |
79 | maxLength => 64, | |
80 | optional => 1, | |
81 | }, | |
82 | target => get_standard_option('pmg-email-address', { | |
83 | description => "The target email address (where to deliver fetched mails).", | |
84 | optional => 1, | |
85 | }), | |
a81ce1a5 DM |
86 | }; |
87 | ||
411caf3f | 88 | our $fetchmail_create_properties = clone($fetchmail_properties); |
6eedc769 DM |
89 | delete $fetchmail_create_properties->{id}; |
90 | foreach my $k (qw(server protocol user pass target)) { | |
91 | delete $fetchmail_create_properties->{$k}->{optional}; | |
92 | } | |
93 | ||
c3346bf1 DM |
94 | __PACKAGE__->register_method ({ |
95 | name => 'index', | |
96 | path => '', | |
97 | method => 'GET', | |
98 | description => "List fetchmail users.", | |
99 | permissions => { check => [ 'admin', 'audit' ] }, | |
100 | proxyto => 'master', | |
a81ce1a5 | 101 | protected => 1, |
c3346bf1 DM |
102 | parameters => { |
103 | additionalProperties => 0, | |
104 | properties => {}, | |
105 | }, | |
106 | returns => { | |
107 | type => 'array', | |
108 | items => { | |
109 | type => "object", | |
a81ce1a5 | 110 | properties => $fetchmail_properties, |
c3346bf1 DM |
111 | }, |
112 | links => [ { rel => 'child', href => "{id}" } ], | |
113 | }, | |
114 | code => sub { | |
115 | my ($param) = @_; | |
116 | ||
117 | my $fmcfg = PVE::INotify::read_file('fetchmailrc'); | |
118 | ||
119 | my $res = []; | |
120 | ||
121 | foreach my $id (sort keys %$fmcfg) { | |
122 | push @$res, $fmcfg->{$id}; | |
123 | } | |
124 | ||
125 | return $res; | |
126 | }}); | |
127 | ||
a81ce1a5 DM |
128 | __PACKAGE__->register_method ({ |
129 | name => 'read', | |
130 | path => '{id}', | |
131 | method => 'GET', | |
132 | description => "Read fetchmail user configuration.", | |
133 | proxyto => 'master', | |
134 | permissions => { check => [ 'admin', 'audit' ] }, | |
135 | protected => 1, | |
136 | parameters => { | |
137 | additionalProperties => 0, | |
138 | properties => { | |
139 | id => $fetchmail_properties->{id}, | |
140 | }, | |
141 | }, | |
142 | returns => { | |
143 | type => "object", | |
144 | properties => $fetchmail_properties, | |
145 | }, | |
146 | code => sub { | |
147 | my ($param) = @_; | |
148 | ||
149 | my $fmcfg = PVE::INotify::read_file('fetchmailrc'); | |
150 | ||
151 | my $data = $fmcfg->{$param->{id}}; | |
152 | die "Fetchmail entry '$param->{id}' does not exist\n" | |
153 | if !$data; | |
154 | ||
155 | return $data; | |
156 | }}); | |
157 | ||
6eedc769 DM |
158 | __PACKAGE__->register_method ({ |
159 | name => 'create', | |
160 | path => '', | |
161 | method => 'POST', | |
162 | description => "Create fetchmail user configuration.", | |
163 | protected => 1, | |
164 | permissions => { check => [ 'admin' ] }, | |
165 | proxyto => 'master', | |
166 | parameters => { | |
167 | additionalProperties => 0, | |
168 | properties => $fetchmail_create_properties, | |
169 | }, | |
170 | returns => $fetchmail_properties->{id}, | |
171 | code => sub { | |
172 | my ($param) = @_; | |
173 | ||
174 | my $id; | |
175 | ||
176 | my $code = sub { | |
177 | ||
178 | my $fmcfg = PVE::INotify::read_file('fetchmailrc'); | |
179 | ||
180 | for (my $i = 0; $i < 9999; $i++) { | |
181 | my $tmpid = sprintf("proxmox%04d", $i); | |
182 | if (!defined($fmcfg->{$tmpid})) { | |
183 | $id = $tmpid; | |
184 | last; | |
185 | } | |
186 | } | |
187 | die "unable to find free Fetchmail entry ID\n" | |
188 | if !defined($id); | |
189 | ||
190 | my $entry = { id => $id }; | |
191 | foreach my $k (keys %$param) { | |
192 | $entry->{$k} = $param->{$k}; | |
193 | } | |
194 | ||
195 | $fmcfg->{$id} = $entry; | |
196 | ||
197 | PVE::INotify::write_file('fetchmailrc', $fmcfg); | |
198 | }; | |
199 | ||
200 | PMG::Config::lock_config($code, "update fechtmail configuration failed"); | |
201 | ||
202 | return $id; | |
203 | }}); | |
204 | ||
a81ce1a5 DM |
205 | __PACKAGE__->register_method ({ |
206 | name => 'write', | |
207 | path => '{id}', | |
208 | method => 'PUT', | |
209 | description => "Update fetchmail user configuration.", | |
210 | protected => 1, | |
211 | permissions => { check => [ 'admin' ] }, | |
212 | proxyto => 'master', | |
213 | parameters => { | |
214 | additionalProperties => 0, | |
215 | properties => $fetchmail_properties, | |
216 | }, | |
217 | returns => { type => 'null' }, | |
218 | code => sub { | |
219 | my ($param) = @_; | |
220 | ||
c16893a6 DM |
221 | my $id = extract_param($param, 'id'); |
222 | ||
a81ce1a5 DM |
223 | my $code = sub { |
224 | ||
225 | my $fmcfg = PVE::INotify::read_file('fetchmailrc'); | |
226 | ||
c16893a6 DM |
227 | my $data = $fmcfg->{$id}; |
228 | die "Fetchmail entry '$id' does not exist\n" | |
a81ce1a5 DM |
229 | if !$data; |
230 | ||
c16893a6 | 231 | foreach my $k (keys %$param) { |
a81ce1a5 DM |
232 | $data->{$k} = $param->{$k}; |
233 | } | |
234 | ||
235 | PVE::INotify::write_file('fetchmailrc', $fmcfg); | |
236 | }; | |
237 | ||
238 | PMG::Config::lock_config($code, "update fechtmail configuration failed"); | |
239 | ||
240 | return undef; | |
241 | }}); | |
242 | ||
9e4d0766 DM |
243 | __PACKAGE__->register_method ({ |
244 | name => 'delete', | |
245 | path => '{id}', | |
246 | method => 'DELETE', | |
247 | description => "Delete a fetchmail configuration entry.", | |
248 | protected => 1, | |
249 | permissions => { check => [ 'admin' ] }, | |
250 | proxyto => 'master', | |
251 | parameters => { | |
252 | additionalProperties => 0, | |
253 | properties => { | |
254 | id => $fetchmail_properties->{id}, | |
255 | } | |
256 | }, | |
257 | returns => { type => 'null' }, | |
258 | code => sub { | |
259 | my ($param) = @_; | |
260 | ||
261 | my $id = extract_param($param, 'id'); | |
262 | ||
263 | my $code = sub { | |
264 | ||
265 | my $fmcfg = PVE::INotify::read_file('fetchmailrc'); | |
266 | ||
267 | die "Fetchmail entry '$id' does not exist\n" | |
268 | if !$fmcfg->{$id}; | |
269 | ||
270 | delete $fmcfg->{$id}; | |
271 | ||
272 | PVE::INotify::write_file('fetchmailrc', $fmcfg); | |
273 | }; | |
274 | ||
275 | PMG::Config::lock_config($code, "delete fechtmail configuration failed"); | |
276 | ||
277 | return undef; | |
278 | }}); | |
279 | ||
c3346bf1 | 280 | 1; |