blob: 5c511f4f26d606820ff473f4c79af629004027c3 [file] [log] [blame]
Matthias Andreas Benkardb382b102021-01-02 15:32:21 +01001<?php
2function fwdhost($_action, $_data = null) {
3 require_once $_SERVER['DOCUMENT_ROOT'] . '/inc/spf.inc.php';
4 global $redis;
5 global $lang;
6 $_data_log = $_data;
7 switch ($_action) {
8 case 'add':
9 global $lang;
10 if ($_SESSION['mailcow_cc_role'] != "admin") {
11 $_SESSION['return'][] = array(
12 'type' => 'danger',
13 'log' => array(__FUNCTION__, $_action, $_data_log),
14 'msg' => 'access_denied'
15 );
16 return false;
17 }
18 $source = $_data['hostname'];
19 $host = trim($_data['hostname']);
20 $filter_spam = (isset($_data['filter_spam']) && $_data['filter_spam'] == 1) ? 1 : 0;
21 if (preg_match('/^[0-9a-fA-F:\/]+$/', $host)) { // IPv6 address
22 $hosts = array($host);
23 }
24 elseif (preg_match('/^[0-9\.\/]+$/', $host)) { // IPv4 address
25 $hosts = array($host);
26 }
27 else {
28 $hosts = get_outgoing_hosts_best_guess($host);
29 }
30 if (empty($hosts)) {
31 $_SESSION['return'][] = array(
32 'type' => 'danger',
33 'log' => array(__FUNCTION__, $_action, $_data_log),
34 'msg' => array('invalid_host', htmlspecialchars($host))
35 );
36 return false;
37 }
38 foreach ($hosts as $host) {
39 try {
40 $redis->hSet('WHITELISTED_FWD_HOST', $host, $source);
41 if ($filter_spam == 0) {
42 $redis->hSet('KEEP_SPAM', $host, 1);
43 }
44 elseif ($redis->hGet('KEEP_SPAM', $host)) {
45 $redis->hDel('KEEP_SPAM', $host);
46 }
47 }
48 catch (RedisException $e) {
49 $_SESSION['return'][] = array(
50 'type' => 'danger',
51 'log' => array(__FUNCTION__, $_action, $_data_log),
52 'msg' => array('redis_error', $e)
53 );
54 return false;
55 }
56 }
57 $_SESSION['return'][] = array(
58 'type' => 'success',
59 'log' => array(__FUNCTION__, $_action, $_data_log),
60 'msg' => array('forwarding_host_added', htmlspecialchars(implode(', ', $hosts)))
61 );
62 break;
63 case 'edit':
64 global $lang;
65 if ($_SESSION['mailcow_cc_role'] != "admin") {
66 $_SESSION['return'][] = array(
67 'type' => 'danger',
68 'log' => array(__FUNCTION__, $_action, $_data_log),
69 'msg' => 'access_denied'
70 );
71 return false;
72 }
73 $fwdhosts = (array)$_data['fwdhost'];
74 foreach ($fwdhosts as $fwdhost) {
75 $is_now = fwdhost('details', $fwdhost);
76 if (!empty($is_now)) {
77 $keep_spam = (isset($_data['keep_spam'])) ? $_data['keep_spam'] : $is_now['keep_spam'];
78 }
79 else {
80 $_SESSION['return'][] = array(
81 'type' => 'danger',
82 'log' => array(__FUNCTION__, $_action, $_data_log),
83 'msg' => 'access_denied'
84 );
85 continue;
86 }
87 try {
88 if ($keep_spam == 1) {
89 $redis->hSet('KEEP_SPAM', $fwdhost, 1);
90 }
91 else {
92 $redis->hDel('KEEP_SPAM', $fwdhost);
93 }
94 }
95 catch (RedisException $e) {
96 $_SESSION['return'][] = array(
97 'type' => 'danger',
98 'log' => array(__FUNCTION__, $_action, $_data_log),
99 'msg' => array('redis_error', $e)
100 );
101 continue;
102 }
103 $_SESSION['return'][] = array(
104 'type' => 'success',
105 'log' => array(__FUNCTION__, $_action, $_data_log),
106 'msg' => array('object_modified', htmlspecialchars($fwdhost))
107 );
108 }
109 break;
110 case 'delete':
111 $hosts = (array)$_data['forwardinghost'];
112 foreach ($hosts as $host) {
113 try {
114 $redis->hDel('WHITELISTED_FWD_HOST', $host);
115 $redis->hDel('KEEP_SPAM', $host);
116 }
117 catch (RedisException $e) {
118 $_SESSION['return'][] = array(
119 'type' => 'danger',
120 'log' => array(__FUNCTION__, $_action, $_data_log),
121 'msg' => array('redis_error', $e)
122 );
123 continue;
124 }
125 $_SESSION['return'][] = array(
126 'type' => 'success',
127 'log' => array(__FUNCTION__, $_action, $_data_log),
128 'msg' => array('forwarding_host_removed', htmlspecialchars($host))
129 );
130 }
131 break;
132 case 'get':
133 if ($_SESSION['mailcow_cc_role'] != "admin") {
134 return false;
135 }
136 $fwdhostsdata = array();
137 try {
138 $fwd_hosts = $redis->hGetAll('WHITELISTED_FWD_HOST');
139 if (!empty($fwd_hosts)) {
140 foreach ($fwd_hosts as $fwd_host => $source) {
141 $keep_spam = ($redis->hGet('KEEP_SPAM', $fwd_host)) ? "yes" : "no";
142 $fwdhostsdata[] = array(
143 'host' => $fwd_host,
144 'source' => $source,
145 'keep_spam' => $keep_spam
146 );
147 }
148 }
149 }
150 catch (RedisException $e) {
151 $_SESSION['return'][] = array(
152 'type' => 'danger',
153 'log' => array(__FUNCTION__, $_action, $_data_log),
154 'msg' => array('redis_error', $e)
155 );
156 return false;
157 }
158 return $fwdhostsdata;
159 break;
160 case 'details':
161 $fwdhostdetails = array();
162 if (!isset($_data) || empty($_data)) {
163 return false;
164 }
165 try {
166 if ($source = $redis->hGet('WHITELISTED_FWD_HOST', $_data)) {
167 $fwdhostdetails['host'] = $_data;
168 $fwdhostdetails['source'] = $source;
169 $fwdhostdetails['keep_spam'] = ($redis->hGet('KEEP_SPAM', $_data)) ? "yes" : "no";
170 }
171 }
172 catch (RedisException $e) {
173 $_SESSION['return'][] = array(
174 'type' => 'danger',
175 'log' => array(__FUNCTION__, $_action, $_data_log),
176 'msg' => array('redis_error', $e)
177 );
178 return false;
179 }
180 return $fwdhostdetails;
181 break;
182 }
183}