]> git.proxmox.com Git - pmg-api.git/blame - PMG/RuleDB/Remove.pm
Add default rulename of 'unknown' to Actions
[pmg-api.git] / PMG / RuleDB / Remove.pm
CommitLineData
758c7b6b
DM
1package PMG::RuleDB::Remove;
2
3use strict;
4use warnings;
758c7b6b
DM
5use DBI;
6use Digest::SHA;
7use MIME::Words;
8use MIME::Entity;
9use Encode;
10
11use PVE::SafeSyslog;
12
13use PMG::Utils;
14use PMG::ModGroup;
15use PMG::RuleDB::Object;
16
17use base qw(PMG::RuleDB::Object);
18
19sub otype {
20 return 4007;
21}
22
23sub otype_text {
24 return 'Remove attachments';
25}
26
27sub oclass {
28 return 'action';
29}
30
758c7b6b
DM
31sub oisedit {
32 return 1;
33}
34
35sub final {
36 return 0;
37}
38
39sub priority {
40 return 40;
41}
42
43sub new {
44 my ($type, $all, $text, $ogroup) = @_;
45
46 my $class = ref($type) || $type;
47
48 $all = 0 if !defined ($all);
49
7a2cf7e6 50 my $self = $class->SUPER::new($class->otype(), $ogroup);
758c7b6b
DM
51
52 $self->{all} = $all;
53 $self->{text} = $text;
54
55 return $self;
56}
57
58sub load_attr {
59 my ($type, $ruledb, $id, $ogroup, $value) = @_;
60
61 my $class = ref($type) || $type;
62
9ef3f143 63 defined ($value) || die "undefined value: ERROR";
758c7b6b
DM
64
65 my $obj;
66
67 if ($value =~ m/^([01])(\:(.*))?$/s) {
68 $obj = $class->new($1, $3, $ogroup);
69 } else {
70 $obj = $class->new(0, undef, $ogroup);
71 }
72
73 $obj->{id} = $id;
74
75 $obj->{digest} = Digest::SHA::sha1_hex($id, $value, $ogroup);
76
77 return $obj;
78}
79
80sub save {
81 my ($self, $ruledb) = @_;
82
9ef3f143 83 defined($self->{ogroup}) || die "undefined ogroup: ERROR";
758c7b6b
DM
84
85 my $value = $self->{all} ? '1' : '0';
86
87 if ($self->{text}) {
88 $value .= ":$self->{text}";
89 }
90
91 if (defined ($self->{id})) {
92 # update
93
94 $ruledb->{dbh}->do(
95 "UPDATE Object SET Value = ? WHERE ID = ?",
96 undef, $value, $self->{id});
97
98 } else {
99 # insert
100
101 my $sth = $ruledb->{dbh}->prepare(
102 "INSERT INTO Object (Objectgroup_ID, ObjectType, Value) " .
103 "VALUES (?, ?, ?);");
104
105 $sth->execute($self->ogroup, $self->otype, $value);
106
107 $self->{id} = PMG::Utils::lastid($ruledb->{dbh}, 'object_id_seq');
108 }
109
110 return $self->{id};
111}
112
113sub delete_marked_parts {
365d5b95 114 my ($self, $queue, $entity, $html, $rtype, $marks, $rulename) = @_;
758c7b6b
DM
115
116 my $nparts = [];
117
118 my $pn = $entity->parts;
119 for (my $i = 0; $i < $pn; $i++) {
120 my $part = $entity->parts($i);
121
122 my ($id, $found);
123
124 if ($id = $part->head->mime_attr('x-proxmox-tmp-aid')) {
125 chomp $id;
126
127 if ($self->{all}) {
128 my $ctype_part = $part->head->mime_type;
129 if (!($i == 0 && $ctype_part =~ m|text/.*|i)) {
130 $found = 1;
131 }
132 } else {
133 foreach my $m (@$marks) {
134 $found = 1 if $m eq $id;
135 }
136 }
137
138 }
139
140 if ($found) {
141
142 my $on = PMG::Utils::extract_filename($part->head) || '';
143
144 my $text = PMG::Utils::subst_values($html, { FILENAME => $on } );
145
146 my $fname = "REMOVED_ATTACHMENT_$id." . ($rtype eq "text/html" ? "html" : "txt");
147
148 my $ent = MIME::Entity->build(
149 Type => $rtype,
150 Charset => 'UTF-8',
151 Encoding => "quoted-printable",
152 Filename => $fname,
153 Disposition => "attachment",
154 Data => encode('UTF-8', $text));
155
156 push (@$nparts, $ent);
157
365d5b95
SI
158 syslog ('info', "%s: removed attachment $id ('%s', rule: %s)",
159 $queue->{logid}, $on, $rulename);
758c7b6b
DM
160
161 } else {
162 $self->delete_marked_parts($queue, $part, $html, $rtype, $marks);
163 push (@$nparts, $part);
164 }
165 }
166
167 $entity->parts ($nparts);
168}
169
170sub execute {
171 my ($self, $queue, $ruledb, $mod_group, $targets,
172 $msginfo, $vars, $marks) = @_;
173
6c65ab40 174 my $rulename = $vars->{RULE} // 'unknown';
365d5b95 175
758c7b6b
DM
176 if (!$self->{all} && ($#$marks == -1)) {
177 # no marks
178 return;
179 }
180
181 my $subgroups = $mod_group->subgroups ($targets);
182
183 my $html = PMG::Utils::subst_values($self->{text}, $vars);
184
185 $html = "This attachment was removed: __FILENAME__\n" if !$html;
186
187 my $rtype = "text/plain";
188
189 if ($html =~ m/\<\w+\>/s) {
190 $rtype = "text/html";
191 }
192
193 foreach my $ta (@$subgroups) {
194 my ($tg, $entity) = (@$ta[0], @$ta[1]);
195
196 # handle singlepart mails
197 my $ctype = $entity->head->mime_type;
198 if (!$entity->is_multipart && (!$self->{all} || $ctype !~ m|text/.*|i)) {
199 $entity->make_multipart();
200 my $first_part = $entity->parts(0);
201 $first_part->head->mime_attr('x-proxmox-tmp-aid' => $entity->head->mime_attr('x-proxmox-tmp-aid'));
202 $entity->head->delete('x-proxmox-tmp-aid');
203 }
204
365d5b95 205 $self->delete_marked_parts($queue, $entity, $html, $rtype, $marks, $rulename);
758c7b6b
DM
206
207 if ($msginfo->{testmode}) {
208 $entity->head->mime_attr('Content-type.boundary' => '------=_TEST123456') if $entity->is_multipart;
209 }
210 }
211}
212
213sub short_desc {
214 my $self = shift;
215
216 if ($self->{all}) {
217 return "remove all attachments";
218 } else {
219 return "remove matching attachments";
220 }
221}
222
46eec8b4
DC
223sub properties {
224 my ($class) = @_;
225
226 return {
227 all => {
228 description => "Remove all attachments",
229 type => 'boolean',
230 optional => 1,
231 },
232 text => {
233 description => "The replacement text.",
234 type => 'string',
235 maxLength => 2048
236 }
237 };
238}
239
240sub get {
241 my ($self) = @_;
242
243 return {
244 text => $self->{text},
245 all => $self->{all},
246 };
247}
248
249sub update {
250 my ($self, $param) = @_;
251
252 $self->{text} = $param->{text};
253 $self->{all} = $param->{all} ? 1 : 0;
254}
758c7b6b
DM
255
2561;
257__END__
258
259=head1 PMG::RuleDB::Remove
260
261Remove attachments.