PageRenderTime 42ms CodeModel.GetById 16ms RepoModel.GetById 0ms app.codeStats 0ms

/libraries/joomla/environment/response.php

http://github.com/joomla/joomla-platform
PHP | 335 lines | 139 code | 40 blank | 156 comment | 21 complexity | 3d35051edc6c33efe82c3072de9a97a1 MD5 | raw file
Possible License(s): GPL-2.0, LGPL-2.1
  1. <?php
  2. /**
  3. * @package Joomla.Platform
  4. * @subpackage Environment
  5. *
  6. * @copyright Copyright (C) 2005 - 2013 Open Source Matters, Inc. All rights reserved.
  7. * @license GNU General Public License version 2 or later; see LICENSE
  8. */
  9. defined('JPATH_PLATFORM') or die;
  10. /**
  11. * JResponse Class.
  12. *
  13. * This class serves to provide the Joomla Platform with a common interface to access
  14. * response variables. This includes header and body.
  15. *
  16. * @package Joomla.Platform
  17. * @subpackage Environment
  18. * @since 11.1
  19. */
  20. class JResponse
  21. {
  22. /**
  23. * @var array Body
  24. * @since 11.1
  25. */
  26. protected static $body = array();
  27. /**
  28. * @var boolean Cachable
  29. * @since 11.1
  30. */
  31. protected static $cachable = false;
  32. /**
  33. * @var array Headers
  34. * @since 11.1
  35. */
  36. protected static $headers = array();
  37. /**
  38. * Set/get cachable state for the response.
  39. *
  40. * If $allow is set, sets the cachable state of the response. Always returns current state.
  41. *
  42. * @param boolean $allow True to allow browser caching.
  43. *
  44. * @return boolean True if browser caching should be allowed
  45. *
  46. * @since 11.1
  47. */
  48. public static function allowCache($allow = null)
  49. {
  50. if (!is_null($allow))
  51. {
  52. self::$cachable = (bool) $allow;
  53. }
  54. return self::$cachable;
  55. }
  56. /**
  57. * Set a header.
  58. *
  59. * If $replace is true, replaces any headers already defined with that $name.
  60. *
  61. * @param string $name The name of the header to set.
  62. * @param string $value The value of the header to set.
  63. * @param boolean $replace True to replace any existing headers by name.
  64. *
  65. * @return void
  66. *
  67. * @since 11.1
  68. */
  69. public static function setHeader($name, $value, $replace = false)
  70. {
  71. $name = (string) $name;
  72. $value = (string) $value;
  73. if ($replace)
  74. {
  75. foreach (self::$headers as $key => $header)
  76. {
  77. if ($name == $header['name'])
  78. {
  79. unset(self::$headers[$key]);
  80. }
  81. }
  82. }
  83. self::$headers[] = array('name' => $name, 'value' => $value);
  84. }
  85. /**
  86. * Return array of headers.
  87. *
  88. * @return array
  89. *
  90. * @since 11.1
  91. */
  92. public static function getHeaders()
  93. {
  94. return self::$headers;
  95. }
  96. /**
  97. * Clear headers.
  98. *
  99. * @return void
  100. *
  101. * @since 11.1
  102. */
  103. public static function clearHeaders()
  104. {
  105. self::$headers = array();
  106. }
  107. /**
  108. * Send all headers.
  109. *
  110. * @return void
  111. *
  112. * @since 11.1
  113. */
  114. public static function sendHeaders()
  115. {
  116. if (!headers_sent())
  117. {
  118. foreach (self::$headers as $header)
  119. {
  120. if ('status' == strtolower($header['name']))
  121. {
  122. // 'status' headers indicate an HTTP status, and need to be handled slightly differently
  123. header(ucfirst(strtolower($header['name'])) . ': ' . $header['value'], null, (int) $header['value']);
  124. }
  125. else
  126. {
  127. header($header['name'] . ': ' . $header['value'], false);
  128. }
  129. }
  130. }
  131. }
  132. /**
  133. * Set body content.
  134. *
  135. * If body content already defined, this will replace it.
  136. *
  137. * @param string $content The content to set to the response body.
  138. *
  139. * @return void
  140. *
  141. * @since 11.1
  142. */
  143. public static function setBody($content)
  144. {
  145. self::$body = array((string) $content);
  146. }
  147. /**
  148. * Prepend content to the body content
  149. *
  150. * @param string $content The content to prepend to the response body.
  151. *
  152. * @return void
  153. *
  154. * @since 11.1
  155. */
  156. public static function prependBody($content)
  157. {
  158. array_unshift(self::$body, (string) $content);
  159. }
  160. /**
  161. * Append content to the body content
  162. *
  163. * @param string $content The content to append to the response body.
  164. *
  165. * @return void
  166. *
  167. * @since 11.1
  168. */
  169. public static function appendBody($content)
  170. {
  171. array_push(self::$body, (string) $content);
  172. }
  173. /**
  174. * Return the body content
  175. *
  176. * @param boolean $toArray Whether or not to return the body content as an array of strings or as a single string; defaults to false.
  177. *
  178. * @return string array
  179. *
  180. * @since 11.1
  181. */
  182. public static function getBody($toArray = false)
  183. {
  184. if ($toArray)
  185. {
  186. return self::$body;
  187. }
  188. ob_start();
  189. foreach (self::$body as $content)
  190. {
  191. echo $content;
  192. }
  193. return ob_get_clean();
  194. }
  195. /**
  196. * Sends all headers prior to returning the string
  197. *
  198. * @param boolean $compress If true, compress the data
  199. *
  200. * @return string
  201. *
  202. * @since 11.1
  203. */
  204. public static function toString($compress = false)
  205. {
  206. $data = self::getBody();
  207. // Don't compress something if the server is going to do it anyway. Waste of time.
  208. if ($compress && !ini_get('zlib.output_compression') && ini_get('output_handler') != 'ob_gzhandler')
  209. {
  210. $data = self::compress($data);
  211. }
  212. if (self::allowCache() === false)
  213. {
  214. self::setHeader('Cache-Control', 'no-cache', false);
  215. // HTTP 1.0
  216. self::setHeader('Pragma', 'no-cache');
  217. }
  218. self::sendHeaders();
  219. return $data;
  220. }
  221. /**
  222. * Compress the data
  223. *
  224. * Checks the accept encoding of the browser and compresses the data before
  225. * sending it to the client.
  226. *
  227. * @param string $data Content to compress for output.
  228. *
  229. * @return string compressed data
  230. *
  231. * @note Replaces _compress method in 11.1
  232. * @since 11.1
  233. */
  234. protected static function compress($data)
  235. {
  236. $encoding = self::clientEncoding();
  237. if (!$encoding)
  238. {
  239. return $data;
  240. }
  241. if (!extension_loaded('zlib') || ini_get('zlib.output_compression'))
  242. {
  243. return $data;
  244. }
  245. if (headers_sent())
  246. {
  247. return $data;
  248. }
  249. if (connection_status() !== 0)
  250. {
  251. return $data;
  252. }
  253. // Ideal level
  254. $level = 4;
  255. /*
  256. $size = strlen($data);
  257. $crc = crc32($data);
  258. $gzdata = "\x1f\x8b\x08\x00\x00\x00\x00\x00";
  259. $gzdata .= gzcompress($data, $level);
  260. $gzdata = substr($gzdata, 0, strlen($gzdata) - 4);
  261. $gzdata .= pack("V",$crc) . pack("V", $size);
  262. */
  263. $gzdata = gzencode($data, $level);
  264. self::setHeader('Content-Encoding', $encoding);
  265. self::setHeader('X-Content-Encoded-By', 'Joomla! 1.6');
  266. return $gzdata;
  267. }
  268. /**
  269. * Check, whether client supports compressed data
  270. *
  271. * @return boolean
  272. *
  273. * @since 11.1
  274. * @note Replaces _clientEncoding method from 11.1
  275. */
  276. protected static function clientEncoding()
  277. {
  278. if (!isset($_SERVER['HTTP_ACCEPT_ENCODING']))
  279. {
  280. return false;
  281. }
  282. $encoding = false;
  283. if (false !== strpos($_SERVER['HTTP_ACCEPT_ENCODING'], 'gzip'))
  284. {
  285. $encoding = 'gzip';
  286. }
  287. if (false !== strpos($_SERVER['HTTP_ACCEPT_ENCODING'], 'x-gzip'))
  288. {
  289. $encoding = 'x-gzip';
  290. }
  291. return $encoding;
  292. }
  293. }