File indexing completed on 2024-12-29 05:28:07
0001 <?php 0002 /** 0003 * Zend Framework 0004 * 0005 * LICENSE 0006 * 0007 * This source file is subject to the new BSD license that is bundled 0008 * with this package in the file LICENSE.txt. 0009 * It is also available through the world-wide-web at this URL: 0010 * http://framework.zend.com/license/new-bsd 0011 * If you did not receive a copy of the license and are unable to 0012 * obtain it through the world-wide-web, please send an email 0013 * to license@zend.com so we can send you a copy immediately. 0014 * 0015 * @category Zend 0016 * @package Zend_Test 0017 * @subpackage PHPUnit 0018 * @copyright Copyright (c) 2005-2015 Zend Technologies USA Inc. (http://www.zend.com) 0019 * @license http://framework.zend.com/license/new-bsd New BSD License 0020 * @version $Id$ 0021 */ 0022 0023 /** 0024 * Response header PHPUnit Constraint 0025 * 0026 * @uses PHPUnit_Framework_Constraint 0027 * @category Zend 0028 * @package Zend_Test 0029 * @subpackage PHPUnit 0030 * @copyright Copyright (c) 2005-2015 Zend Technologies USA Inc. (http://www.zend.com) 0031 * @license http://framework.zend.com/license/new-bsd New BSD License 0032 */ 0033 class Zend_Test_PHPUnit_Constraint_ResponseHeader41 extends PHPUnit_Framework_Constraint 0034 { 0035 /**#@+ 0036 * Assertion type constants 0037 */ 0038 const ASSERT_RESPONSE_CODE = 'assertResponseCode'; 0039 const ASSERT_HEADER = 'assertHeader'; 0040 const ASSERT_HEADER_CONTAINS = 'assertHeaderContains'; 0041 const ASSERT_HEADER_REGEX = 'assertHeaderRegex'; 0042 /**#@-*/ 0043 0044 /** 0045 * Current assertion type 0046 * @var string 0047 */ 0048 protected $_assertType = null; 0049 0050 /** 0051 * Available assertion types 0052 * @var array 0053 */ 0054 protected $_assertTypes = array( 0055 self::ASSERT_RESPONSE_CODE, 0056 self::ASSERT_HEADER, 0057 self::ASSERT_HEADER_CONTAINS, 0058 self::ASSERT_HEADER_REGEX, 0059 ); 0060 0061 /** 0062 * @var int Response code 0063 */ 0064 protected $_code = 200; 0065 0066 /** 0067 * @var int Actual response code 0068 */ 0069 protected $_actualCode = null; 0070 0071 /** 0072 * @var string Header 0073 */ 0074 protected $_header = null; 0075 0076 /** 0077 * @var string pattern against which to compare header content 0078 */ 0079 protected $_match = null; 0080 0081 /** 0082 * Whether or not assertion is negated 0083 * @var bool 0084 */ 0085 protected $_negate = false; 0086 0087 /** 0088 * Constructor; setup constraint state 0089 * 0090 * @return void 0091 */ 0092 public function __construct() 0093 { 0094 } 0095 0096 /** 0097 * Indicate negative match 0098 * 0099 * @param bool $flag 0100 * @return void 0101 */ 0102 public function setNegate($flag = true) 0103 { 0104 $this->_negate = $flag; 0105 } 0106 0107 /** 0108 * Evaluate an object to see if it fits the constraints 0109 * 0110 * @param object of Zend_Controller_Response_Abstract to be evaluated 0111 * @param null|string Assertion type 0112 * @param int|string HTTP response code to evaluate against | header string (haystack) 0113 * @param string (optional) match (needle), may be required depending on assertion type 0114 * @return bool 0115 * NOTE: 0116 * Drastic changes up to PHPUnit 3.5.15 this was: 0117 * public function evaluate($other, $assertType = null) 0118 * In PHPUnit 3.6.0 they changed the interface into this: 0119 * public function evaluate($other, $description = '', $returnResult = FALSE) 0120 * We use the new interface for PHP-strict checking, but emulate the old one 0121 */ 0122 public function evaluate($response, $assertType = '', $variable = FALSE) 0123 { 0124 if (!$response instanceof Zend_Controller_Response_Abstract) { 0125 // require_once 'Zend/Test/PHPUnit/Constraint/Exception.php'; 0126 throw new Zend_Test_PHPUnit_Constraint_Exception('Header constraint assertions require a response object'); 0127 } 0128 0129 if (strstr($assertType, 'Not')) { 0130 $this->setNegate(true); 0131 $assertType = str_replace('Not', '', $assertType); 0132 } 0133 0134 if (!in_array($assertType, $this->_assertTypes)) { 0135 // require_once 'Zend/Test/PHPUnit/Constraint/Exception.php'; 0136 throw new Zend_Test_PHPUnit_Constraint_Exception(sprintf('Invalid assertion type "%s" provided to %s constraint', $assertType, __CLASS__)); 0137 } 0138 0139 $this->_assertType = $assertType; 0140 0141 $argv = func_get_args(); 0142 $argc = func_num_args(); 0143 0144 switch ($assertType) { 0145 case self::ASSERT_RESPONSE_CODE: 0146 if (3 > $argc) { 0147 // require_once 'Zend/Test/PHPUnit/Constraint/Exception.php'; 0148 throw new Zend_Test_PHPUnit_Constraint_Exception('No response code provided against which to match'); 0149 } 0150 $this->_code = $code = $argv[2]; 0151 return ($this->_negate) 0152 ? $this->_notCode($response, $code) 0153 : $this->_code($response, $code); 0154 case self::ASSERT_HEADER: 0155 if (3 > $argc) { 0156 // require_once 'Zend/Test/PHPUnit/Constraint/Exception.php'; 0157 throw new Zend_Test_PHPUnit_Constraint_Exception('No header provided against which to match'); 0158 } 0159 $this->_header = $header = $argv[2]; 0160 return ($this->_negate) 0161 ? $this->_notHeader($response, $header) 0162 : $this->_header($response, $header); 0163 case self::ASSERT_HEADER_CONTAINS: 0164 if (4 > $argc) { 0165 // require_once 'Zend/Test/PHPUnit/Constraint/Exception.php'; 0166 throw new Zend_Test_PHPUnit_Constraint_Exception('Both a header name and content to match are required for ' . $assertType); 0167 } 0168 $this->_header = $header = $argv[2]; 0169 $this->_match = $match = $argv[3]; 0170 return ($this->_negate) 0171 ? $this->_notHeaderContains($response, $header, $match) 0172 : $this->_headerContains($response, $header, $match); 0173 case self::ASSERT_HEADER_REGEX: 0174 if (4 > $argc) { 0175 // require_once 'Zend/Test/PHPUnit/Constraint/Exception.php'; 0176 throw new Zend_Test_PHPUnit_Constraint_Exception('Both a header name and content to match are required for ' . $assertType); 0177 } 0178 $this->_header = $header = $argv[2]; 0179 $this->_match = $match = $argv[3]; 0180 return ($this->_negate) 0181 ? $this->_notHeaderRegex($response, $header, $match) 0182 : $this->_headerRegex($response, $header, $match); 0183 default: 0184 // require_once 'Zend/Test/PHPUnit/Constraint/Exception.php'; 0185 throw new Zend_Test_PHPUnit_Constraint_Exception('Invalid assertion type ' . $assertType); 0186 } 0187 } 0188 0189 /** 0190 * Report Failure 0191 * 0192 * @see PHPUnit_Framework_Constraint for implementation details 0193 * @param mixed CSS selector path 0194 * @param string Failure description 0195 * @param object Cannot be used, null 0196 * @return void 0197 * @throws PHPUnit_Framework_ExpectationFailedException 0198 * NOTE: 0199 * Drastic changes up to PHPUnit 3.5.15 this was: 0200 * public function fail($other, $description, $not = false) 0201 * In PHPUnit 3.6.0 they changed the interface into this: 0202 * protected function fail($other, $description, PHPUnit_Framework_ComparisonFailure $comparisonFailure = NULL) 0203 * We use the new interface for PHP-strict checking 0204 * NOTE 2: 0205 * Interface changed again in PHPUnit 4.1.0 because of refactoring to SebastianBergmann\Comparator 0206 */ 0207 public function fail($other, $description, \SebastianBergmann\Comparator\ComparisonFailure $cannot_be_used = NULL) 0208 { 0209 // require_once 'Zend/Test/PHPUnit/Constraint/Exception.php'; 0210 switch ($this->_assertType) { 0211 case self::ASSERT_RESPONSE_CODE: 0212 $failure = 'Failed asserting response code "%s"'; 0213 if ($this->_negate) { 0214 $failure = 'Failed asserting response code IS NOT "%s"'; 0215 } 0216 $failure = sprintf($failure, $this->_code); 0217 if (!$this->_negate && $this->_actualCode) { 0218 $failure .= sprintf(PHP_EOL . 'Was "%s"', $this->_actualCode); 0219 } 0220 break; 0221 case self::ASSERT_HEADER: 0222 $failure = 'Failed asserting response header "%s" found'; 0223 if ($this->_negate) { 0224 $failure = 'Failed asserting response response header "%s" WAS NOT found'; 0225 } 0226 $failure = sprintf($failure, $this->_header); 0227 break; 0228 case self::ASSERT_HEADER_CONTAINS: 0229 $failure = 'Failed asserting response header "%s" exists and contains "%s"'; 0230 if ($this->_negate) { 0231 $failure = 'Failed asserting response header "%s" DOES NOT CONTAIN "%s"'; 0232 } 0233 $failure = sprintf($failure, $this->_header, $this->_match); 0234 break; 0235 case self::ASSERT_HEADER_REGEX: 0236 $failure = 'Failed asserting response header "%s" exists and matches regex "%s"'; 0237 if ($this->_negate) { 0238 $failure = 'Failed asserting response header "%s" DOES NOT MATCH regex "%s"'; 0239 } 0240 $failure = sprintf($failure, $this->_header, $this->_match); 0241 break; 0242 default: 0243 throw new Zend_Test_PHPUnit_Constraint_Exception('Invalid assertion type ' . __FUNCTION__); 0244 } 0245 0246 if (!empty($description)) { 0247 $failure = $description . "\n" . $failure; 0248 } 0249 0250 throw new Zend_Test_PHPUnit_Constraint_Exception($failure); 0251 } 0252 0253 /** 0254 * Complete implementation 0255 * 0256 * @return string 0257 */ 0258 public function toString() 0259 { 0260 return ''; 0261 } 0262 0263 /** 0264 * Compare response code for positive match 0265 * 0266 * @param Zend_Controller_Response_Abstract $response 0267 * @param int $code 0268 * @return bool 0269 */ 0270 protected function _code(Zend_Controller_Response_Abstract $response, $code) 0271 { 0272 $test = $this->_getCode($response); 0273 $this->_actualCode = $test; 0274 return ($test == $code); 0275 } 0276 0277 /** 0278 * Compare response code for negative match 0279 * 0280 * @param Zend_Controller_Response_Abstract $response 0281 * @param int $code 0282 * @return bool 0283 */ 0284 protected function _notCode(Zend_Controller_Response_Abstract $response, $code) 0285 { 0286 $test = $this->_getCode($response); 0287 return ($test != $code); 0288 } 0289 0290 /** 0291 * Retrieve response code 0292 * 0293 * @param Zend_Controller_Response_Abstract $response 0294 * @return int 0295 */ 0296 protected function _getCode(Zend_Controller_Response_Abstract $response) 0297 { 0298 $test = $response->getHttpResponseCode(); 0299 if (null === $test) { 0300 $test = 200; 0301 } 0302 return $test; 0303 } 0304 0305 /** 0306 * Positive check for response header presence 0307 * 0308 * @param Zend_Controller_Response_Abstract $response 0309 * @param string $header 0310 * @return bool 0311 */ 0312 protected function _header(Zend_Controller_Response_Abstract $response, $header) 0313 { 0314 return (null !== $this->_getHeader($response, $header)); 0315 } 0316 0317 /** 0318 * Negative check for response header presence 0319 * 0320 * @param Zend_Controller_Response_Abstract $response 0321 * @param string $header 0322 * @return bool 0323 */ 0324 protected function _notHeader(Zend_Controller_Response_Abstract $response, $header) 0325 { 0326 return (null === $this->_getHeader($response, $header)); 0327 } 0328 0329 /** 0330 * Retrieve response header 0331 * 0332 * @param Zend_Controller_Response_Abstract $response 0333 * @param string $header 0334 * @return string|null 0335 */ 0336 protected function _getHeader(Zend_Controller_Response_Abstract $response, $header) 0337 { 0338 $headers = $response->sendHeaders(); 0339 $header = strtolower($header); 0340 if (array_key_exists($header, $headers)) { 0341 return $headers[$header]; 0342 } 0343 return null; 0344 } 0345 0346 /** 0347 * Positive check for header contents matching pattern 0348 * 0349 * @param Zend_Controller_Response_Abstract $response 0350 * @param string $header 0351 * @param string $match 0352 * @return bool 0353 */ 0354 protected function _headerContains(Zend_Controller_Response_Abstract $response, $header, $match) 0355 { 0356 if (null === ($fullHeader = $this->_getHeader($response, $header))) { 0357 return false; 0358 } 0359 0360 $contents = str_replace($header . ': ', '', $fullHeader); 0361 0362 return (strstr($contents, $match) !== false); 0363 } 0364 0365 /** 0366 * Negative check for header contents matching pattern 0367 * 0368 * @param Zend_Controller_Response_Abstract $response 0369 * @param string $header 0370 * @param string $match 0371 * @return bool 0372 */ 0373 protected function _notHeaderContains(Zend_Controller_Response_Abstract $response, $header, $match) 0374 { 0375 if (null === ($fullHeader = $this->_getHeader($response, $header))) { 0376 return true; 0377 } 0378 0379 $contents = str_replace($header . ': ', '', $fullHeader); 0380 0381 return (strstr($contents, $match) === false); 0382 } 0383 0384 /** 0385 * Positive check for header contents matching regex 0386 * 0387 * @param Zend_Controller_Response_Abstract $response 0388 * @param string $header 0389 * @param string $pattern 0390 * @return bool 0391 */ 0392 protected function _headerRegex(Zend_Controller_Response_Abstract $response, $header, $pattern) 0393 { 0394 if (null === ($fullHeader = $this->_getHeader($response, $header))) { 0395 return false; 0396 } 0397 0398 $contents = str_replace($header . ': ', '', $fullHeader); 0399 0400 return preg_match($pattern, $contents); 0401 } 0402 0403 /** 0404 * Negative check for header contents matching regex 0405 * 0406 * @param Zend_Controller_Response_Abstract $response 0407 * @param string $header 0408 * @param string $pattern 0409 * @return bool 0410 */ 0411 protected function _notHeaderRegex(Zend_Controller_Response_Abstract $response, $header, $pattern) 0412 { 0413 if (null === ($fullHeader = $this->_getHeader($response, $header))) { 0414 return true; 0415 } 0416 0417 $contents = str_replace($header . ': ', '', $fullHeader); 0418 0419 return !preg_match($pattern, $contents); 0420 } 0421 }