json_api.php 40 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075
  1. <?php
  2. /*
  3. edit/alias => POST data:
  4. {
  5. address: {a, b, c}, (where a, b, c represent alias addresses)
  6. active: 1 (0 or 1)
  7. }
  8. delete/alias => POST data:
  9. {
  10. address: {a, b, c}, (where a, b, c represent alias addresses)
  11. }
  12. */
  13. header('Content-Type: application/json');
  14. require_once $_SERVER['DOCUMENT_ROOT'] . '/inc/prerequisites.inc.php';
  15. error_reporting(0);
  16. function api_log($_data) {
  17. global $redis;
  18. $data_var = array();
  19. foreach ($_data as $data => &$value) {
  20. if ($data == 'csrf_token') {
  21. continue;
  22. }
  23. if ($value = json_decode($value, true)) {
  24. unset($value["csrf_token"]);
  25. foreach ($value as $key => &$val) {
  26. if(preg_match("/pass/i", $key)) {
  27. $val = '*';
  28. }
  29. }
  30. $value = json_encode($value);
  31. }
  32. $data_var[] = $data . "='" . $value . "'";
  33. }
  34. try {
  35. $log_line = array(
  36. 'time' => time(),
  37. 'uri' => $_SERVER['REQUEST_URI'],
  38. 'method' => $_SERVER['REQUEST_METHOD'],
  39. 'remote' => get_remote_ip(),
  40. 'data' => implode(', ', $data_var)
  41. );
  42. $redis->lPush('API_LOG', json_encode($log_line));
  43. }
  44. catch (RedisException $e) {
  45. $_SESSION['return'][] = array(
  46. 'type' => 'danger',
  47. 'msg' => 'Redis: '.$e
  48. );
  49. return false;
  50. }
  51. }
  52. api_log($_POST);
  53. if (isset($_SESSION['mailcow_cc_role']) || isset($_SESSION['pending_mailcow_cc_username'])) {
  54. if (isset($_GET['query'])) {
  55. $query = explode('/', $_GET['query']);
  56. $action = (isset($query[0])) ? $query[0] : null;
  57. $category = (isset($query[1])) ? $query[1] : null;
  58. $object = (isset($query[2])) ? $query[2] : null;
  59. $extra = (isset($query[3])) ? $query[3] : null;
  60. $request_incomplete = json_encode(array(
  61. 'type' => 'error',
  62. 'msg' => 'Cannot find attributes in post data'
  63. ));
  64. switch ($action) {
  65. case "add":
  66. function process_add_return($return) {
  67. $generic_failure = json_encode(array(
  68. 'type' => 'error',
  69. 'msg' => 'Cannot add item'
  70. ));
  71. $generic_success = json_encode(array(
  72. 'type' => 'success',
  73. 'msg' => 'Task completed'
  74. ));
  75. if ($return === false) {
  76. echo isset($_SESSION['return']) ? json_encode($_SESSION['return']) : $generic_failure;
  77. }
  78. else {
  79. echo isset($_SESSION['return']) ? json_encode($_SESSION['return']) : $generic_success;
  80. }
  81. }
  82. if (!isset($_POST['attr'])) {
  83. echo $request_incomplete;
  84. exit;
  85. }
  86. else {
  87. $attr = (array)json_decode($_POST['attr'], true);
  88. unset($attr['csrf_token']);
  89. }
  90. switch ($category) {
  91. case "time_limited_alias":
  92. process_add_return(mailbox('add', 'time_limited_alias', $attr));
  93. break;
  94. case "relayhost":
  95. process_add_return(relayhost('add', $attr));
  96. break;
  97. case "rsetting":
  98. process_add_return(rsettings('add', $attr));
  99. break;
  100. case "mailbox":
  101. process_add_return(mailbox('add', 'mailbox', $attr));
  102. break;
  103. case "domain":
  104. process_add_return(mailbox('add', 'domain', $attr));
  105. break;
  106. case "resource":
  107. process_add_return(mailbox('add', 'resource', $attr));
  108. break;
  109. case "alias":
  110. process_add_return(mailbox('add', 'alias', $attr));
  111. break;
  112. case "filter":
  113. process_add_return(mailbox('add', 'filter', $attr));
  114. break;
  115. case "domain-policy":
  116. process_add_return(policy('add', 'domain', $attr));
  117. break;
  118. case "mailbox-policy":
  119. process_add_return(policy('add', 'mailbox', $attr));
  120. break;
  121. case "alias-domain":
  122. process_add_return(mailbox('add', 'alias_domain', $attr));
  123. break;
  124. case "fwdhost":
  125. process_add_return(fwdhost('add', $attr));
  126. break;
  127. case "dkim":
  128. process_add_return(dkim('add', $attr));
  129. break;
  130. case "dkim_duplicate":
  131. process_add_return(dkim('duplicate', $attr));
  132. break;
  133. case "dkim_import":
  134. process_add_return(dkim('import', $attr));
  135. break;
  136. case "domain-admin":
  137. process_add_return(domain_admin('add', $attr));
  138. break;
  139. case "syncjob":
  140. process_add_return(mailbox('add', 'syncjob', $attr));
  141. break;
  142. case "bcc":
  143. process_add_return(bcc('add', $attr));
  144. break;
  145. case "recipient_map":
  146. process_add_return(recipient_map('add', $attr));
  147. break;
  148. }
  149. break;
  150. case "get":
  151. function process_get_return($data) {
  152. echo (!isset($data) || empty($data)) ? '{}' : json_encode($data, JSON_UNESCAPED_UNICODE | JSON_PRETTY_PRINT);
  153. }
  154. switch ($category) {
  155. case "rspamd":
  156. switch ($object) {
  157. case "actions":
  158. $curl = curl_init();
  159. curl_setopt($curl, CURLOPT_UNIX_SOCKET_PATH, '/rspamd-sock/rspamd.sock');
  160. curl_setopt($curl, CURLOPT_URL,"http://rspamd/stat");
  161. curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
  162. $data = curl_exec($curl);
  163. if ($data) {
  164. $return = array();
  165. $stats_array = json_decode($data, true)['actions'];
  166. $stats_array['soft reject'] = $stats_array['soft reject'] + $stats_array['greylist'];
  167. unset($stats_array['greylist']);
  168. foreach ($stats_array as $action => $count) {
  169. $return[] = array($action, $count);
  170. }
  171. echo json_encode($return, JSON_UNESCAPED_UNICODE | JSON_PRETTY_PRINT);
  172. }
  173. elseif (!isset($data) || empty($data)) {
  174. echo '{}';
  175. }
  176. break;
  177. }
  178. break;
  179. case "domain":
  180. switch ($object) {
  181. case "all":
  182. $domains = mailbox('get', 'domains');
  183. if (!empty($domains)) {
  184. foreach ($domains as $domain) {
  185. if ($details = mailbox('get', 'domain_details', $domain)) {
  186. $data[] = $details;
  187. }
  188. else {
  189. continue;
  190. }
  191. }
  192. process_get_return($data);
  193. }
  194. else {
  195. echo '{}';
  196. }
  197. break;
  198. default:
  199. $data = mailbox('get', 'domain_details', $object);
  200. process_get_return($data);
  201. break;
  202. }
  203. break;
  204. case "rl-domain":
  205. switch ($object) {
  206. case "all":
  207. $domains = array_merge(mailbox('get', 'domains'), mailbox('get', 'alias_domains'));
  208. if (!empty($domains)) {
  209. foreach ($domains as $domain) {
  210. if ($details = ratelimit('get', 'domain', $domain)) {
  211. $details['domain'] = $domain;
  212. $data[] = $details;
  213. }
  214. else {
  215. continue;
  216. }
  217. }
  218. process_get_return($data);
  219. }
  220. else {
  221. echo '{}';
  222. }
  223. break;
  224. default:
  225. $data = ratelimit('get', 'domain', $object);
  226. process_get_return($data);
  227. break;
  228. }
  229. break;
  230. case "rl-mbox":
  231. switch ($object) {
  232. case "all":
  233. $domains = mailbox('get', 'domains');
  234. if (!empty($domains)) {
  235. foreach ($domains as $domain) {
  236. $mailboxes = mailbox('get', 'mailboxes', $domain);
  237. if (!empty($mailboxes)) {
  238. foreach ($mailboxes as $mailbox) {
  239. if ($details = ratelimit('get', 'mailbox', $mailbox)) {
  240. $details['mailbox'] = $mailbox;
  241. $data[] = $details;
  242. }
  243. else {
  244. continue;
  245. }
  246. }
  247. }
  248. }
  249. process_get_return($data);
  250. }
  251. else {
  252. echo '{}';
  253. }
  254. break;
  255. default:
  256. $data = ratelimit('get', 'mailbox', $object);
  257. process_get_return($data);
  258. break;
  259. }
  260. break;
  261. case "relayhost":
  262. switch ($object) {
  263. case "all":
  264. $relayhosts = relayhost('get');
  265. if (!empty($relayhosts)) {
  266. foreach ($relayhosts as $relayhost) {
  267. if ($details = relayhost('details', $relayhost['id'])) {
  268. $data[] = $details;
  269. }
  270. else {
  271. continue;
  272. }
  273. }
  274. process_get_return($data);
  275. }
  276. else {
  277. echo '{}';
  278. }
  279. break;
  280. default:
  281. $data = relayhost('details', $object);
  282. process_get_return($data);
  283. break;
  284. }
  285. break;
  286. case "rsetting":
  287. switch ($object) {
  288. case "all":
  289. $rsettings = rsettings('get');
  290. if (!empty($rsettings)) {
  291. foreach ($rsettings as $rsetting) {
  292. if ($details = rsettings('details', $rsetting['id'])) {
  293. $data[] = $details;
  294. }
  295. else {
  296. continue;
  297. }
  298. }
  299. process_get_return($data);
  300. }
  301. else {
  302. echo '{}';
  303. }
  304. break;
  305. default:
  306. $data = rsetting('details', $object);
  307. process_get_return($data);
  308. break;
  309. }
  310. break;
  311. case "oauth2-client":
  312. switch ($object) {
  313. case "all":
  314. $clients = oauth2('get', 'clients');
  315. if (!empty($clients)) {
  316. foreach ($clients as $client) {
  317. if ($details = oauth2('details', 'client', $client)) {
  318. $data[] = $details;
  319. }
  320. else {
  321. continue;
  322. }
  323. }
  324. process_get_return($data);
  325. }
  326. else {
  327. echo '{}';
  328. }
  329. break;
  330. default:
  331. $data = oauth2('details', 'client', $object);
  332. process_get_return($data);
  333. break;
  334. }
  335. break;
  336. case "logs":
  337. switch ($object) {
  338. case "dovecot":
  339. // 0 is first record, so empty is fine
  340. if (isset($extra)) {
  341. $extra = preg_replace('/[^\d\-]/i', '', $extra);
  342. $logs = get_logs('dovecot-mailcow', $extra);
  343. }
  344. else {
  345. $logs = get_logs('dovecot-mailcow');
  346. }
  347. echo (isset($logs) && !empty($logs)) ? json_encode($logs, JSON_UNESCAPED_UNICODE | JSON_PRETTY_PRINT) : '{}';
  348. break;
  349. case "netfilter":
  350. // 0 is first record, so empty is fine
  351. if (isset($extra)) {
  352. $extra = preg_replace('/[^\d\-]/i', '', $extra);
  353. $logs = get_logs('netfilter-mailcow', $extra);
  354. }
  355. else {
  356. $logs = get_logs('netfilter-mailcow');
  357. }
  358. echo (isset($logs) && !empty($logs)) ? json_encode($logs, JSON_UNESCAPED_UNICODE | JSON_PRETTY_PRINT) : '{}';
  359. break;
  360. case "postfix":
  361. // 0 is first record, so empty is fine
  362. if (isset($extra)) {
  363. $extra = preg_replace('/[^\d\-]/i', '', $extra);
  364. $logs = get_logs('postfix-mailcow', $extra);
  365. }
  366. else {
  367. $logs = get_logs('postfix-mailcow');
  368. }
  369. echo (isset($logs) && !empty($logs)) ? json_encode($logs, JSON_UNESCAPED_UNICODE | JSON_PRETTY_PRINT) : '{}';
  370. break;
  371. case "autodiscover":
  372. // 0 is first record, so empty is fine
  373. if (isset($extra)) {
  374. $extra = preg_replace('/[^\d\-]/i', '', $extra);
  375. $logs = get_logs('autodiscover-mailcow', $extra);
  376. }
  377. else {
  378. $logs = get_logs('autodiscover-mailcow');
  379. }
  380. echo (isset($logs) && !empty($logs)) ? json_encode($logs, JSON_UNESCAPED_UNICODE | JSON_PRETTY_PRINT) : '{}';
  381. break;
  382. case "sogo":
  383. // 0 is first record, so empty is fine
  384. if (isset($extra)) {
  385. $extra = preg_replace('/[^\d\-]/i', '', $extra);
  386. $logs = get_logs('sogo-mailcow', $extra);
  387. }
  388. else {
  389. $logs = get_logs('sogo-mailcow');
  390. }
  391. echo (isset($logs) && !empty($logs)) ? json_encode($logs, JSON_UNESCAPED_UNICODE | JSON_PRETTY_PRINT) : '{}';
  392. break;
  393. case "ui":
  394. // 0 is first record, so empty is fine
  395. if (isset($extra)) {
  396. $extra = preg_replace('/[^\d\-]/i', '', $extra);
  397. $logs = get_logs('mailcow-ui', $extra);
  398. }
  399. else {
  400. $logs = get_logs('mailcow-ui');
  401. }
  402. echo (isset($logs) && !empty($logs)) ? json_encode($logs, JSON_UNESCAPED_UNICODE | JSON_PRETTY_PRINT) : '{}';
  403. break;
  404. case "watchdog":
  405. // 0 is first record, so empty is fine
  406. if (isset($extra)) {
  407. $extra = preg_replace('/[^\d\-]/i', '', $extra);
  408. $logs = get_logs('watchdog-mailcow', $extra);
  409. }
  410. else {
  411. $logs = get_logs('watchdog-mailcow');
  412. }
  413. echo (isset($logs) && !empty($logs)) ? json_encode($logs, JSON_UNESCAPED_UNICODE | JSON_PRETTY_PRINT) : '{}';
  414. break;
  415. case "acme":
  416. // 0 is first record, so empty is fine
  417. if (isset($extra)) {
  418. $extra = preg_replace('/[^\d\-]/i', '', $extra);
  419. $logs = get_logs('acme-mailcow', $extra);
  420. }
  421. else {
  422. $logs = get_logs('acme-mailcow');
  423. }
  424. echo (isset($logs) && !empty($logs)) ? json_encode($logs, JSON_UNESCAPED_UNICODE | JSON_PRETTY_PRINT) : '{}';
  425. break;
  426. case "api":
  427. // 0 is first record, so empty is fine
  428. if (isset($extra)) {
  429. $extra = preg_replace('/[^\d\-]/i', '', $extra);
  430. $logs = get_logs('api-mailcow', $extra);
  431. }
  432. else {
  433. $logs = get_logs('api-mailcow');
  434. }
  435. echo (isset($logs) && !empty($logs)) ? json_encode($logs, JSON_UNESCAPED_UNICODE | JSON_PRETTY_PRINT) : '{}';
  436. break;
  437. case "rspamd-history":
  438. // 0 is first record, so empty is fine
  439. if (isset($extra)) {
  440. $extra = preg_replace('/[^\d\-]/i', '', $extra);
  441. $logs = get_logs('rspamd-history', $extra);
  442. }
  443. else {
  444. $logs = get_logs('rspamd-history');
  445. }
  446. echo (isset($logs) && !empty($logs)) ? json_encode($logs, JSON_UNESCAPED_UNICODE | JSON_PRETTY_PRINT) : '{}';
  447. break;
  448. }
  449. break;
  450. case "mailbox":
  451. switch ($object) {
  452. case "all":
  453. $domains = mailbox('get', 'domains');
  454. if (!empty($domains)) {
  455. foreach ($domains as $domain) {
  456. $mailboxes = mailbox('get', 'mailboxes', $domain);
  457. if (!empty($mailboxes)) {
  458. foreach ($mailboxes as $mailbox) {
  459. if ($details = mailbox('get', 'mailbox_details', $mailbox)) {
  460. $data[] = $details;
  461. }
  462. else {
  463. continue;
  464. }
  465. }
  466. }
  467. }
  468. process_get_return($data);
  469. }
  470. else {
  471. echo '{}';
  472. }
  473. break;
  474. default:
  475. $data = mailbox('get', 'mailbox_details', $object);
  476. process_get_return($data);
  477. break;
  478. }
  479. break;
  480. case "syncjobs":
  481. switch ($object) {
  482. case "all":
  483. $domains = mailbox('get', 'domains');
  484. if (!empty($domains)) {
  485. foreach ($domains as $domain) {
  486. $mailboxes = mailbox('get', 'mailboxes', $domain);
  487. if (!empty($mailboxes)) {
  488. foreach ($mailboxes as $mailbox) {
  489. $syncjobs = mailbox('get', 'syncjobs', $mailbox);
  490. if (!empty($syncjobs)) {
  491. foreach ($syncjobs as $syncjob) {
  492. if (isset($extra)) {
  493. $details = mailbox('get', 'syncjob_details', $syncjob, explode(',', $extra));
  494. }
  495. else {
  496. $details = mailbox('get', 'syncjob_details', $syncjob);
  497. }
  498. if ($details) {
  499. $data[] = $details;
  500. }
  501. else {
  502. continue;
  503. }
  504. }
  505. }
  506. }
  507. }
  508. }
  509. process_get_return($data);
  510. }
  511. else {
  512. echo '{}';
  513. }
  514. break;
  515. default:
  516. $syncjobs = mailbox('get', 'syncjobs', $object);
  517. if (!empty($syncjobs)) {
  518. foreach ($syncjobs as $syncjob) {
  519. if (isset($extra)) {
  520. $details = mailbox('get', 'syncjob_details', $syncjob, explode(',', $extra));
  521. }
  522. else {
  523. $details = mailbox('get', 'syncjob_details', $syncjob);
  524. }
  525. if ($details) {
  526. $data[] = $details;
  527. }
  528. else {
  529. continue;
  530. }
  531. }
  532. }
  533. process_get_return($data);
  534. break;
  535. }
  536. break;
  537. case "active-user-sieve":
  538. if (isset($object)) {
  539. $sieve_filter = mailbox('get', 'active_user_sieve', $object);
  540. if (!empty($sieve_filter)) {
  541. $data[] = $sieve_filter;
  542. }
  543. }
  544. process_get_return($data);
  545. break;
  546. case "filters":
  547. switch ($object) {
  548. case "all":
  549. $domains = mailbox('get', 'domains');
  550. if (!empty($domains)) {
  551. foreach ($domains as $domain) {
  552. $mailboxes = mailbox('get', 'mailboxes', $domain);
  553. if (!empty($mailboxes)) {
  554. foreach ($mailboxes as $mailbox) {
  555. $filters = mailbox('get', 'filters', $mailbox);
  556. if (!empty($filters)) {
  557. foreach ($filters as $filter) {
  558. if ($details = mailbox('get', 'filter_details', $filter)) {
  559. $data[] = $details;
  560. }
  561. else {
  562. continue;
  563. }
  564. }
  565. }
  566. }
  567. }
  568. }
  569. process_get_return($data);
  570. }
  571. else {
  572. echo '{}';
  573. }
  574. break;
  575. default:
  576. $filters = mailbox('get', 'filters', $object);
  577. if (!empty($filters)) {
  578. foreach ($filters as $filter) {
  579. if ($details = mailbox('get', 'filter_details', $filter)) {
  580. $data[] = $details;
  581. }
  582. else {
  583. continue;
  584. }
  585. }
  586. }
  587. process_get_return($data);
  588. break;
  589. }
  590. break;
  591. case "bcc":
  592. switch ($object) {
  593. case "all":
  594. $bcc_items = bcc('get');
  595. if (!empty($bcc_items)) {
  596. foreach ($bcc_items as $bcc_item) {
  597. if ($details = bcc('details', $bcc_item)) {
  598. $data[] = $details;
  599. }
  600. else {
  601. continue;
  602. }
  603. }
  604. }
  605. process_get_return($data);
  606. break;
  607. default:
  608. $data = bcc('details', $object);
  609. if (!empty($data)) {
  610. $data[] = $details;
  611. }
  612. process_get_return($data);
  613. break;
  614. }
  615. break;
  616. case "recipient_map":
  617. switch ($object) {
  618. case "all":
  619. $recipient_map_items = recipient_map('get');
  620. if (!empty($recipient_map_items)) {
  621. foreach ($recipient_map_items as $recipient_map_item) {
  622. if ($details = recipient_map('details', $recipient_map_item)) {
  623. $data[] = $details;
  624. }
  625. else {
  626. continue;
  627. }
  628. }
  629. }
  630. process_get_return($data);
  631. break;
  632. default:
  633. $data = recipient_map('details', $object);
  634. if (!empty($data)) {
  635. $data[] = $details;
  636. }
  637. process_get_return($data);
  638. break;
  639. }
  640. break;
  641. case "policy_wl_mailbox":
  642. switch ($object) {
  643. default:
  644. $data = policy('get', 'mailbox', $object)['whitelist'];
  645. process_get_return($data);
  646. break;
  647. }
  648. break;
  649. case "policy_bl_mailbox":
  650. switch ($object) {
  651. default:
  652. $data = policy('get', 'mailbox', $object)['blacklist'];
  653. process_get_return($data);
  654. break;
  655. }
  656. break;
  657. case "policy_wl_domain":
  658. switch ($object) {
  659. default:
  660. $data = policy('get', 'domain', $object)['whitelist'];
  661. process_get_return($data);
  662. break;
  663. }
  664. break;
  665. case "policy_bl_domain":
  666. switch ($object) {
  667. default:
  668. $data = policy('get', 'domain', $object)['blacklist'];
  669. process_get_return($data);
  670. break;
  671. }
  672. break;
  673. case "time_limited_aliases":
  674. switch ($object) {
  675. default:
  676. $data = mailbox('get', 'time_limited_aliases', $object);
  677. process_get_return($data);
  678. break;
  679. }
  680. break;
  681. case "resource":
  682. switch ($object) {
  683. case "all":
  684. $domains = mailbox('get', 'domains');
  685. if (!empty($domains)) {
  686. foreach ($domains as $domain) {
  687. $resources = mailbox('get', 'resources', $domain);
  688. if (!empty($resources)) {
  689. foreach ($resources as $resource) {
  690. if ($details = mailbox('get', 'resource_details', $resource)) {
  691. $data[] = $details;
  692. }
  693. else {
  694. continue;
  695. }
  696. }
  697. }
  698. }
  699. process_get_return($data);
  700. }
  701. else {
  702. echo '{}';
  703. }
  704. break;
  705. default:
  706. $data = mailbox('get', 'resource_details', $object);
  707. process_get_return($data);
  708. break;
  709. }
  710. break;
  711. case "fwdhost":
  712. switch ($object) {
  713. case "all":
  714. process_get_return(fwdhost('get'));
  715. break;
  716. default:
  717. process_get_return(fwdhost('details', $object));
  718. break;
  719. }
  720. break;
  721. case "quarantine":
  722. // "all" will not print details
  723. switch ($object) {
  724. case "all":
  725. process_get_return(quarantine('get'));
  726. break;
  727. default:
  728. process_get_return(quarantine('details', $object));
  729. break;
  730. }
  731. break;
  732. case "alias-domain":
  733. switch ($object) {
  734. case "all":
  735. $alias_domains = mailbox('get', 'alias_domains');
  736. if (!empty($alias_domains)) {
  737. foreach ($alias_domains as $alias_domain) {
  738. if ($details = mailbox('get', 'alias_domain_details', $alias_domain)) {
  739. $data[] = $details;
  740. }
  741. else {
  742. continue;
  743. }
  744. }
  745. }
  746. process_get_return($data);
  747. break;
  748. default:
  749. process_get_return(mailbox('get', 'alias_domain_details', $object));
  750. break;
  751. }
  752. break;
  753. case "alias":
  754. switch ($object) {
  755. case "all":
  756. $domains = array_merge(mailbox('get', 'domains'), mailbox('get', 'alias_domains'));
  757. if (!empty($domains)) {
  758. foreach ($domains as $domain) {
  759. $aliases = mailbox('get', 'aliases', $domain);
  760. if (!empty($aliases)) {
  761. foreach ($aliases as $alias) {
  762. if ($details = mailbox('get', 'alias_details', $alias)) {
  763. $data[] = $details;
  764. }
  765. else {
  766. continue;
  767. }
  768. }
  769. }
  770. }
  771. process_get_return($data);
  772. }
  773. else {
  774. echo '{}';
  775. }
  776. break;
  777. default:
  778. process_get_return(mailbox('get', 'alias_details', $object));
  779. break;
  780. }
  781. break;
  782. case "domain-admin":
  783. switch ($object) {
  784. case "all":
  785. $domain_admins = domain_admin('get');
  786. if (!empty($domain_admins)) {
  787. foreach ($domain_admins as $domain_admin) {
  788. if ($details = domain_admin('details', $domain_admin)) {
  789. $data[] = $details;
  790. }
  791. else {
  792. continue;
  793. }
  794. }
  795. process_get_return($data);
  796. }
  797. else {
  798. echo '{}';
  799. }
  800. break;
  801. default:
  802. process_get_return(domain_admin('details', $object));
  803. break;
  804. }
  805. break;
  806. case "u2f-registration":
  807. header('Content-Type: application/javascript');
  808. if (($_SESSION["mailcow_cc_role"] == "admin" || $_SESSION["mailcow_cc_role"] == "domainadmin") && $_SESSION["mailcow_cc_username"] == $object) {
  809. list($req, $sigs) = $u2f->getRegisterData(get_u2f_registrations($object));
  810. $_SESSION['regReq'] = json_encode($req);
  811. $_SESSION['regSigs'] = json_encode($sigs);
  812. echo 'var req = ' . json_encode($req) . ';';
  813. echo 'var registeredKeys = ' . json_encode($sigs) . ';';
  814. echo 'var appId = req.appId;';
  815. echo 'var registerRequests = [{version: req.version, challenge: req.challenge}];';
  816. }
  817. else {
  818. return;
  819. }
  820. break;
  821. case "u2f-authentication":
  822. header('Content-Type: application/javascript');
  823. if (isset($_SESSION['pending_mailcow_cc_username']) && $_SESSION['pending_mailcow_cc_username'] == $object) {
  824. $auth_data = $u2f->getAuthenticateData(get_u2f_registrations($object));
  825. $challenge = $auth_data[0]->challenge;
  826. $appId = $auth_data[0]->appId;
  827. foreach ($auth_data as $each) {
  828. $key = array(); // Empty array
  829. $key['version'] = $each->version;
  830. $key['keyHandle'] = $each->keyHandle;
  831. $registeredKey[] = $key;
  832. }
  833. $_SESSION['authReq'] = json_encode($auth_data);
  834. echo 'var appId = "' . $appId . '";';
  835. echo 'var challenge = ' . json_encode($challenge) . ';';
  836. echo 'var registeredKeys = ' . json_encode($registeredKey) . ';';
  837. }
  838. else {
  839. return;
  840. }
  841. break;
  842. default:
  843. echo '{}';
  844. break;
  845. }
  846. break;
  847. case "delete":
  848. function process_delete_return($return) {
  849. $generic_failure = json_encode(array(
  850. 'type' => 'error',
  851. 'msg' => 'Cannot delete item'
  852. ));
  853. $generic_success = json_encode(array(
  854. 'type' => 'success',
  855. 'msg' => 'Task completed'
  856. ));
  857. if ($return === false) {
  858. echo isset($_SESSION['return']) ? json_encode($_SESSION['return']) : $generic_failure;
  859. }
  860. else {
  861. echo isset($_SESSION['return']) ? json_encode($_SESSION['return']) : $generic_success;
  862. }
  863. }
  864. if (!isset($_POST['items'])) {
  865. echo $request_incomplete;
  866. exit;
  867. }
  868. else {
  869. $items = (array)json_decode($_POST['items'], true);
  870. }
  871. switch ($category) {
  872. case "alias":
  873. process_delete_return(mailbox('delete', 'alias', array('id' => $items)));
  874. break;
  875. case "relayhost":
  876. process_delete_return(relayhost('delete', array('id' => $items)));
  877. break;
  878. case "rsetting":
  879. process_delete_return(rsettings('delete', array('id' => $items)));
  880. break;
  881. case "syncjob":
  882. process_delete_return(mailbox('delete', 'syncjob', array('id' => $items)));
  883. break;
  884. case "filter":
  885. process_delete_return(mailbox('delete', 'filter', array('id' => $items)));
  886. break;
  887. case "qitem":
  888. process_delete_return(quarantine('delete', array('id' => $items)));
  889. break;
  890. case "bcc":
  891. process_delete_return(bcc('delete', array('id' => $items)));
  892. break;
  893. case "recipient_map":
  894. process_delete_return(recipient_map('delete', array('id' => $items)));
  895. break;
  896. case "fwdhost":
  897. process_delete_return(fwdhost('delete', array('forwardinghost' => $items)));
  898. break;
  899. case "dkim":
  900. process_delete_return(dkim('delete', array('domains' => $items)));
  901. break;
  902. case "domain":
  903. file_put_contents('/tmp/dssaa', $items);
  904. process_delete_return(mailbox('delete', 'domain', array('domain' => $items)));
  905. break;
  906. case "alias-domain":
  907. process_delete_return(mailbox('delete', 'alias_domain', array('alias_domain' => $items)));
  908. break;
  909. case "mailbox":
  910. process_delete_return(mailbox('delete', 'mailbox', array('username' => $items)));
  911. break;
  912. case "resource":
  913. process_delete_return(mailbox('delete', 'resource', array('name' => $items)));
  914. break;
  915. case "mailbox-policy":
  916. process_delete_return(policy('delete', 'mailbox', array('prefid' => $items)));
  917. break;
  918. case "domain-policy":
  919. process_delete_return(policy('delete', 'domain', array('prefid' => $items)));
  920. break;
  921. case "time_limited_alias":
  922. process_delete_return(mailbox('delete', 'time_limited_alias', array('address' => $items)));
  923. break;
  924. case "eas_cache":
  925. process_delete_return(mailbox('delete', 'eas_cache', array('username' => $items)));
  926. break;
  927. case "domain-admin":
  928. process_delete_return(domain_admin('delete', array('username' => $items)));
  929. break;
  930. }
  931. break;
  932. case "edit":
  933. function process_edit_return($return) {
  934. $generic_failure = json_encode(array(
  935. 'type' => 'error',
  936. 'msg' => 'Cannot edit item'
  937. ));
  938. $generic_success = json_encode(array(
  939. 'type' => 'success',
  940. 'msg' => 'Task completed'
  941. ));
  942. if ($return === false) {
  943. echo isset($_SESSION['return']) ? json_encode($_SESSION['return']) : $generic_failure;
  944. }
  945. else {
  946. echo isset($_SESSION['return']) ? json_encode($_SESSION['return']) : $generic_success;
  947. }
  948. }
  949. if (!isset($_POST['attr'])) {
  950. echo $request_incomplete;
  951. exit;
  952. }
  953. else {
  954. $attr = (array)json_decode($_POST['attr'], true);
  955. unset($attr['csrf_token']);
  956. $items = isset($_POST['items']) ? (array)json_decode($_POST['items'], true) : null;
  957. }
  958. switch ($category) {
  959. case "bcc":
  960. process_edit_return(bcc('edit', array_merge(array('id' => $items), $attr)));
  961. break;
  962. case "oauth2-client":
  963. process_edit_return(oauth2('edit', 'client', array_merge(array('id' => $items), $attr)));
  964. break;
  965. case "recipient_map":
  966. process_edit_return(recipient_map('edit', array_merge(array('id' => $items), $attr)));
  967. break;
  968. case "alias":
  969. process_edit_return(mailbox('edit', 'alias', array_merge(array('id' => $items), $attr)));
  970. break;
  971. case "app_links":
  972. process_edit_return(customize('edit', 'app_links', $attr));
  973. break;
  974. case "relayhost":
  975. process_edit_return(relayhost('edit', array_merge(array('id' => $items), $attr)));
  976. break;
  977. case "rsetting":
  978. process_edit_return(rsettings('edit', array_merge(array('id' => $items), $attr)));
  979. break;
  980. case "delimiter_action":
  981. process_edit_return(mailbox('edit', 'delimiter_action', array_merge(array('username' => $items), $attr)));
  982. break;
  983. case "tls_policy":
  984. process_edit_return(mailbox('edit', 'tls_policy', array_merge(array('username' => $items), $attr)));
  985. break;
  986. case "qitem":
  987. process_edit_return(quarantine('edit', array_merge(array('id' => $items), $attr)));
  988. break;
  989. case "quarantine":
  990. process_edit_return(quarantine('edit', $attr));
  991. break;
  992. case "time_limited_alias":
  993. process_edit_return(mailbox('edit', 'time_limited_alias', array_merge(array('address' => $items), $attr)));
  994. break;
  995. case "mailbox":
  996. process_edit_return(mailbox('edit', 'mailbox', array_merge(array('username' => $items), $attr)));
  997. break;
  998. case "syncjob":
  999. process_edit_return(mailbox('edit', 'syncjob', array_merge(array('id' => $items), $attr)));
  1000. break;
  1001. case "filter":
  1002. process_edit_return(mailbox('edit', 'filter', array_merge(array('id' => $items), $attr)));
  1003. break;
  1004. case "resource":
  1005. process_edit_return(mailbox('edit', 'resource', array_merge(array('name' => $items), $attr)));
  1006. break;
  1007. case "domain":
  1008. process_edit_return(mailbox('edit', 'domain', array_merge(array('domain' => $items), $attr)));
  1009. break;
  1010. case "rl-domain":
  1011. process_edit_return(ratelimit('edit', 'domain', array_merge(array('object' => $items), $attr)));
  1012. break;
  1013. case "rl-mbox":
  1014. process_edit_return(ratelimit('edit', 'mailbox', array_merge(array('object' => $items), $attr)));
  1015. break;
  1016. case "alias-domain":
  1017. process_edit_return(mailbox('edit', 'alias_domain', array_merge(array('alias_domain' => $items), $attr)));
  1018. break;
  1019. case "spam-score":
  1020. process_edit_return(mailbox('edit', 'spam_score', array_merge(array('username' => $items), $attr)));
  1021. break;
  1022. case "domain-admin":
  1023. process_edit_return(domain_admin('edit', array_merge(array('username' => $items), $attr)));
  1024. break;
  1025. case "fwdhost":
  1026. process_edit_return(fwdhost('edit', array_merge(array('fwdhost' => $items), $attr)));
  1027. break;
  1028. case "fail2ban":
  1029. process_edit_return(fail2ban('edit', array_merge(array('network' => $items), $attr)));
  1030. break;
  1031. case "ui_texts":
  1032. process_edit_return(customize('edit', 'ui_texts', $attr));
  1033. break;
  1034. case "self":
  1035. if ($_SESSION['mailcow_cc_role'] == "domainadmin") {
  1036. process_edit_return(domain_admin('edit', $attr));
  1037. }
  1038. elseif ($_SESSION['mailcow_cc_role'] == "user") {
  1039. process_edit_return(edit_user_account($attr));
  1040. }
  1041. elseif ($_SESSION['mailcow_cc_role'] == "admin") {
  1042. process_edit_return(edit_admin_account($attr));
  1043. }
  1044. break;
  1045. }
  1046. break;
  1047. }
  1048. }
  1049. }