1c3437056SNickeau<?php 2c3437056SNickeau 3c3437056SNickeau 4c3437056SNickeaunamespace ComboStrap; 5c3437056SNickeau 6c3437056SNickeau 7c3437056SNickeauuse TestRequest; 8c3437056SNickeau 9c3437056SNickeauclass HttpResponse 10c3437056SNickeau{ 11c3437056SNickeau public const EXIT_KEY = 'exit'; 12c3437056SNickeau 13c3437056SNickeau 14c3437056SNickeau const STATUS_NOT_FOUND = 404; 15c3437056SNickeau public const STATUS_ALL_GOOD = 200; 16c3437056SNickeau const STATUS_NOT_MODIFIED = 304; 17c3437056SNickeau const STATUS_PERMANENT_REDIRECT = 301; 18c3437056SNickeau public const STATUS_DOES_NOT_EXIST = 404; 19c3437056SNickeau public const STATUS_UNSUPPORTED_MEDIA_TYPE = 415; 20c3437056SNickeau public const STATUS_BAD_REQUEST = 400; 21c3437056SNickeau public const STATUS_INTERNAL_ERROR = 500; 22c3437056SNickeau public const STATUS_NOT_AUTHORIZED = 401; 23c3437056SNickeau const MESSAGE_ATTRIBUTE = "message"; 24c3437056SNickeau 25c3437056SNickeau /** 26c3437056SNickeau * @var int 27c3437056SNickeau */ 28c3437056SNickeau private $status; 29c3437056SNickeau 30c3437056SNickeau private $canonical = "support"; 31c3437056SNickeau /** 32c3437056SNickeau * @var \Doku_Event 33c3437056SNickeau */ 34c3437056SNickeau private $event; 35c3437056SNickeau /** 36c3437056SNickeau * @var array 37c3437056SNickeau */ 38c3437056SNickeau private $headers = []; 39c3437056SNickeau private $msg; 40c3437056SNickeau 41c3437056SNickeau 42c3437056SNickeau /** 43c3437056SNickeau * Error constructor. 44c3437056SNickeau */ 45c3437056SNickeau public function __construct($status, $msg) 46c3437056SNickeau { 47c3437056SNickeau $this->status = $status; 48c3437056SNickeau $this->msg = $msg; 49c3437056SNickeau } 50c3437056SNickeau 51c3437056SNickeau public static function create(int $status, string $msg = null): HttpResponse 52c3437056SNickeau { 53c3437056SNickeau return new HttpResponse($status, $msg); 54c3437056SNickeau } 55c3437056SNickeau 56c3437056SNickeau 57c3437056SNickeau public function setEvent(\Doku_Event $event): HttpResponse 58c3437056SNickeau { 59c3437056SNickeau $this->event = $event; 60c3437056SNickeau return $this; 61c3437056SNickeau } 62c3437056SNickeau 63c3437056SNickeau public function send($payload = null, $contentType = null) 64c3437056SNickeau { 65c3437056SNickeau 66c3437056SNickeau if ($contentType != null) { 67c3437056SNickeau Http::setMime($contentType); 68c3437056SNickeau } else { 69c3437056SNickeau Http::setMime(Mime::PLAIN_TEXT); 70c3437056SNickeau } 71c3437056SNickeau 72c3437056SNickeau // header should before the status 73c3437056SNickeau // because for instance a `"Location` header changes the status to 302 74c3437056SNickeau foreach ($this->headers as $header) { 75c3437056SNickeau header($header); 76c3437056SNickeau } 77c3437056SNickeau 78c3437056SNickeau if ($this->status !== null) { 79c3437056SNickeau Http::setStatus($this->status); 80c3437056SNickeau } else { 81c3437056SNickeau $status = Http::getStatus(); 82c3437056SNickeau if ($status === null) { 83c3437056SNickeau Http::setStatus(self::STATUS_INTERNAL_ERROR); 84c3437056SNickeau LogUtility::log2file("No status was set for this soft exit, the default was set instead", LogUtility::LVL_MSG_ERROR, $this->canonical); 85c3437056SNickeau } 86c3437056SNickeau } 87c3437056SNickeau 88c3437056SNickeau 89c3437056SNickeau /** 90c3437056SNickeau * Payload 91c3437056SNickeau */ 92c3437056SNickeau if ($payload !== null) { 93c3437056SNickeau echo $payload; 94c3437056SNickeau } 95c3437056SNickeau 96c3437056SNickeau /** 97c3437056SNickeau * Exit 98c3437056SNickeau */ 99c3437056SNickeau if (!PluginUtility::isTest()) { 100*8acada91Sgerardnico if ($this->status !== self::STATUS_ALL_GOOD && $this->msg !== null) { 101*8acada91Sgerardnico // if this is a 304, there is no body, no message 102*8acada91Sgerardnico LogUtility::log2file("Bad Http Response: $this->status : $this->msg", LogUtility::LVL_MSG_ERROR, $this->canonical); 103c3437056SNickeau } 104c3437056SNickeau exit; 105c3437056SNickeau } else { 106c3437056SNickeau 107c3437056SNickeau /** 108c3437056SNickeau * Stop the propagation and prevent the default 109c3437056SNickeau */ 110c3437056SNickeau if ($this->event !== null) { 111c3437056SNickeau $this->event->stopPropagation(); 112c3437056SNickeau $this->event->preventDefault(); 113c3437056SNickeau } 114c3437056SNickeau 115c3437056SNickeau /** 116c3437056SNickeau * Add test info into the request 117c3437056SNickeau */ 118c3437056SNickeau $testRequest = TestRequest::getRunning(); 119c3437056SNickeau 120c3437056SNickeau if ($testRequest !== null) { 121c3437056SNickeau $testRequest->addData(self::EXIT_KEY, $payload); 122c3437056SNickeau } 123c3437056SNickeau 124c3437056SNickeau /** 125c3437056SNickeau * Output buffer 126c3437056SNickeau * Stop the buffer 127c3437056SNickeau * Test request starts a buffer at {@link TestRequest::execute()}, 128c3437056SNickeau * it will capture the body until this point 129c3437056SNickeau */ 130c3437056SNickeau ob_end_clean(); 131c3437056SNickeau /** 132c3437056SNickeau * To avoid phpunit warning `Test code or tested code did not (only) close its own output buffers` 133c3437056SNickeau * and 134c3437056SNickeau * Send the output to the void 135c3437056SNickeau */ 136c3437056SNickeau ob_start(function ($value) { 137c3437056SNickeau }); 138c3437056SNickeau 139c3437056SNickeau } 140c3437056SNickeau } 141c3437056SNickeau 142c3437056SNickeau public function setCanonical($canonical): HttpResponse 143c3437056SNickeau { 144c3437056SNickeau $this->canonical = $canonical; 145c3437056SNickeau return $this; 146c3437056SNickeau } 147c3437056SNickeau 148c3437056SNickeau 149c3437056SNickeau public function addHeader(string $header): HttpResponse 150c3437056SNickeau { 151c3437056SNickeau $this->headers[] = $header; 152c3437056SNickeau return $this; 153c3437056SNickeau } 154c3437056SNickeau 155c3437056SNickeau /** 156c3437056SNickeau * @param string|array $messages 157c3437056SNickeau */ 158c3437056SNickeau public function sendMessage($messages) 159c3437056SNickeau { 160c3437056SNickeau if (is_array($messages) && sizeof($messages) == 0) { 161c3437056SNickeau $messages = ["No information, no errors"]; 162c3437056SNickeau } 163c3437056SNickeau $message = json_encode(["message" => $messages]); 164c3437056SNickeau $this->send($message, Mime::JSON); 165c3437056SNickeau 166c3437056SNickeau } 167c3437056SNickeau 168c3437056SNickeau} 169