ApiController.php 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334
  1. <?php
  2. namespace Opentalent\OtAdmin\Http;
  3. use Opentalent\OtAdmin\Controller\ScanController;
  4. use Opentalent\OtAdmin\Controller\SiteController;
  5. use Psr\Log\LoggerAwareInterface;
  6. use Psr\Log\LoggerAwareTrait;
  7. use TYPO3\CMS\Core\Http\JsonResponse;
  8. use TYPO3\CMS\Core\Http\ServerRequest;
  9. use TYPO3\CMS\Core\Utility\GeneralUtility;
  10. use TYPO3\CMS\Extbase\Object\ObjectManager;
  11. /**
  12. * Actions for Http API calls
  13. *
  14. * @package Opentalent\OtAdmin\Http
  15. */
  16. class ApiController implements LoggerAwareInterface
  17. {
  18. use LoggerAwareTrait;
  19. const ALLOWED_IPS = [
  20. '/^127\.0\.0\.[0-1]$/',
  21. '/^localhost$/',
  22. '/^10\.8\.0\.\d{1,3}$/',
  23. '/^80\.245\.24\.68$/', // prod-front
  24. '/^80\.245\.24\.70$/', // prod-back
  25. '/^80\.245\.24\.72$/', // test
  26. '/^80\.245\.24\.74$/' // preprod
  27. ];
  28. /**
  29. * Returns true if the client Ip is allowed
  30. *
  31. * @param string $clientIp
  32. * @return bool
  33. */
  34. public static function isIpAllowed(string $clientIp) {
  35. foreach (self::ALLOWED_IPS as $ipRule) {
  36. if (preg_match($ipRule, $clientIp)) {
  37. return true;
  38. }
  39. }
  40. return false;
  41. }
  42. /**
  43. * Check that the client Ip is allowed, else throw a Runtime error
  44. *
  45. * @return bool
  46. */
  47. private function assertIpAllowed() {
  48. $clientIp = $_SERVER['REMOTE_ADDR'];
  49. if (!self::isIpAllowed($clientIp)){
  50. $route = $_REQUEST['route'];
  51. $this->logger->error(sprintf(
  52. "OtAdmin API: an attempt was made to call the route " .
  53. $route . " from an non-allowed IP (" . $clientIp . ")"));
  54. throw new \RuntimeException("Not allowed");
  55. }
  56. return true;
  57. }
  58. /**
  59. * Retrieve the organization's id from the given request parameters
  60. *
  61. * @param ServerRequest $request
  62. * @return int
  63. */
  64. private function getOrganizationId(ServerRequest $request) {
  65. $params = $request->getQueryParams();
  66. $organizationId = $params['organization-id'];
  67. if (!$organizationId) {
  68. throw new \RuntimeException("Missing parameter: 'organization-id'");
  69. }
  70. return (int)$organizationId;
  71. }
  72. /**
  73. * -- Target of the route 'site_infos' --
  74. *
  75. * Return the main informations about the organization's website
  76. *
  77. * @param ServerRequest $request
  78. * @return JsonResponse
  79. * @throws \Exception
  80. */
  81. public function getSiteInfosAction(ServerRequest $request) {
  82. $this->assertIpAllowed();
  83. $organizationId = $this->getOrganizationId($request);
  84. $controller = GeneralUtility::makeInstance(ObjectManager::class)->get(SiteController::class);
  85. $infos = $controller->getSiteInfosAction($organizationId);
  86. return new JsonResponse($infos);
  87. }
  88. /**
  89. * -- Target of the route 'site_create' --
  90. * >> Requires a query param named 'organization-id' (int)
  91. *
  92. * Create the organization's website
  93. *
  94. * @param ServerRequest $request
  95. * @return JsonResponse
  96. * @throws \Exception
  97. */
  98. public function createSiteAction(ServerRequest $request) {
  99. $this->assertIpAllowed();
  100. $organizationId = $this->getOrganizationId($request);
  101. $controller = GeneralUtility::makeInstance(ObjectManager::class)->get(SiteController::class);
  102. $rootUid = $controller->createSiteAction($organizationId);
  103. $this->logger->info(sprintf(
  104. "OtAdmin API: A new website has been created with root page uid=" . $rootUid .
  105. " for the organization " . $organizationId));
  106. return new JsonResponse(
  107. [
  108. 'organization_id' => $organizationId,
  109. 'msg' => "A new website has been created with root page uid=" . $rootUid,
  110. 'root_uid' => $rootUid
  111. ]
  112. );
  113. }
  114. /**
  115. * -- Target of the route 'site_update' --
  116. * >> Requires a query param named 'organization-id' (int)
  117. *
  118. * Update the settings of the organization's website
  119. *
  120. * @param ServerRequest $request
  121. * @return JsonResponse
  122. * @throws \Exception
  123. */
  124. public function updateSiteConstantsAction(ServerRequest $request) {
  125. $this->assertIpAllowed();
  126. $organizationId = $this->getOrganizationId($request);
  127. $controller = GeneralUtility::makeInstance(ObjectManager::class)->get(SiteController::class);
  128. $rootUid = $controller->updateSiteConstantsAction($organizationId);
  129. $this->logger->info(sprintf(
  130. "OtAdmin API: The website with root uid " . $rootUid . " has been updated " .
  131. " (organization: " . $organizationId . ")"));
  132. return new JsonResponse(
  133. [
  134. 'organization_id' => $organizationId,
  135. 'msg' => "The website with root uid " . $rootUid . " has been updated",
  136. 'root_uid' => $rootUid
  137. ]
  138. );
  139. }
  140. /**
  141. * -- Target of the route 'site_delete' --
  142. * >> Requires a query param named 'organization-id' (int)
  143. *
  144. * Proceeds to a soft-deletion of the organization's website
  145. *
  146. * @param ServerRequest $request
  147. * @return JsonResponse
  148. * @throws \Exception
  149. */
  150. public function deleteSiteAction(ServerRequest $request) {
  151. $this->assertIpAllowed();
  152. $organizationId = $this->getOrganizationId($request);
  153. $params = $request->getQueryParams();
  154. $redirectTo = isset($params['redirect-to']) ? $params['redirect-to'] : null;
  155. $controller = GeneralUtility::makeInstance(ObjectManager::class)->get(SiteController::class);
  156. $rootUid = $controller->deleteSiteAction($organizationId, false, $redirectTo);
  157. $this->logger->info(sprintf(
  158. "OtAdmin API: The website with root uid " . $rootUid . " has been soft-deleted " .
  159. " (organization: " . $organizationId . ")"));
  160. return new JsonResponse(
  161. [
  162. 'organization_id' => $organizationId,
  163. 'msg' => "The website with root uid " . $rootUid . " has been soft-deleted. Use the /site/undelete route to restore it.",
  164. 'root_uid' => $rootUid
  165. ]
  166. );
  167. }
  168. /**
  169. * -- Target of the route 'site_undelete' --
  170. * >> Requires a query param named 'organization-id' (int)
  171. *
  172. * Restore a soft-deleted organization's website
  173. *
  174. * @param ServerRequest $request
  175. * @return JsonResponse
  176. * @throws \Exception
  177. */
  178. public function undeleteSiteAction(ServerRequest $request) {
  179. $this->assertIpAllowed();
  180. $organizationId = $this->getOrganizationId($request);
  181. $controller = GeneralUtility::makeInstance(ObjectManager::class)->get(SiteController::class);
  182. $rootUid = $controller->undeleteSiteAction($organizationId);
  183. $this->logger->info(sprintf(
  184. "OtAdmin API: The website with root uid " . $rootUid . " has been restored " .
  185. " (organization: " . $organizationId . ")"));
  186. return new JsonResponse(
  187. [
  188. 'organization_id' => $organizationId,
  189. 'msg' => "The website with root uid " . $rootUid . " has been restored",
  190. 'root_uid' => $rootUid
  191. ]
  192. );
  193. }
  194. /**
  195. * -- Target of the route 'site_clearcache' --
  196. * >> Requires a query param named 'organization-id' (int)
  197. *
  198. * Clear the cache of the organization's website
  199. *
  200. * @param ServerRequest $request
  201. * @return JsonResponse
  202. * @throws \Exception
  203. */
  204. public function clearSiteCacheAction(ServerRequest $request) {
  205. $this->assertIpAllowed();
  206. $organizationId = $this->getOrganizationId($request);
  207. $controller = GeneralUtility::makeInstance(ObjectManager::class)->get(SiteController::class);
  208. $rootUid = $controller->clearSiteCacheAction($organizationId);
  209. return new JsonResponse(
  210. [
  211. 'organization_id' => $organizationId,
  212. 'msg' => "The cache has been cleared for the website with root uid " . $rootUid . "",
  213. 'root_uid' => $rootUid
  214. ]
  215. );
  216. }
  217. /**
  218. * -- Target of the route 'site_set_domain' --
  219. * >> Requires a query param named 'organization-id' (int)
  220. *
  221. * Set a new domain for the organization website
  222. *
  223. * @param ServerRequest $request
  224. * @return JsonResponse
  225. * @throws \Exception
  226. */
  227. public function setSiteDomainAction(ServerRequest $request) {
  228. $this->assertIpAllowed();
  229. $organizationId = $this->getOrganizationId($request);
  230. $queryParams = $request->getQueryParams();
  231. $domain = $queryParams['domain'];
  232. if (!$domain) {
  233. throw new \RuntimeException("Missing 'domain' parameter");
  234. }
  235. $redirect = (isset($queryParams['redirect']) && $queryParams['redirect']);
  236. $controller = GeneralUtility::makeInstance(ObjectManager::class)->get(SiteController::class);
  237. $rootUid = $controller->setSiteDomainAction($organizationId, $domain, $redirect);
  238. return new JsonResponse(
  239. [
  240. 'organization_id' => $organizationId,
  241. 'msg' => "The cache has been cleared for the website with root uid " . $rootUid . "",
  242. 'root_uid' => $rootUid
  243. ]
  244. );
  245. }
  246. /**
  247. * -- Target of the route 'site_status' --
  248. * >> Requires a query param named 'organization-id' (int)
  249. *
  250. * Returns the current status of the website
  251. *
  252. * @param ServerRequest $request
  253. * @return JsonResponse
  254. * @throws \Exception
  255. */
  256. public function getSiteStatusAction(ServerRequest $request) {
  257. $this->assertIpAllowed();
  258. $organizationId = $this->getOrganizationId($request);
  259. $controller = GeneralUtility::makeInstance(ObjectManager::class)->get(SiteController::class);
  260. $queryParams = $request->getQueryParams();
  261. $full = (isset($queryParams['full']) && $queryParams['full']);
  262. $status = $controller->getSiteStatusAction($organizationId, $full);
  263. return new JsonResponse($status->toArray());
  264. }
  265. /**
  266. * -- Target of the route 'scan' --
  267. *
  268. * Scan the whole Typo3 database and return the results
  269. *
  270. * @param ServerRequest $request
  271. * @return JsonResponse
  272. * @throws \Exception
  273. */
  274. public function scanAllAction(ServerRequest $request) {
  275. $this->assertIpAllowed();
  276. $controller = GeneralUtility::makeInstance(ObjectManager::class)->get(ScanController::class);
  277. $queryParams = $request->getQueryParams();
  278. $full = (isset($queryParams['full']) && $queryParams['full']);
  279. $results = $controller->scanAllAction($full);
  280. return new JsonResponse($results);
  281. }
  282. }