Exemplo n.º 1
0
 /**
  * Creates a request to be sent over the Internet.
  *
  * For the request to be sent over HTTPS instead of regular HTTP, the input URL should explicitly indicate "https"
  * as the communication protocol to be used. The same applies to FTP/FTPS.
  *
  * When making an `HTTP_POST` request, at least one POST field should be specified with `addPostField` method
  * before sending the request. Likewise, if the request type is `HTTP_UPLOAD`, `HTTP_PUT`, or `FTP_UPLOAD`, the
  * outgoing file's path or outgoing data needs to be provided before sending the request, using either
  * `setUploadFile` or `setUploadData` method.
  *
  * The number of the destination port can be specified in the URL or with `setPort` method.
  *
  * @param  string $url The URL to which the request is to be sent. If no protocol is indicated in the URL, the
  * HTTP protocol is assumed.
  * @param  enum $type **OPTIONAL. Default is** `HTTP_GET`. The type of the request (see [Summary](#summary)).
  * @param  string $downloadDestinationFp **OPTIONAL.** For `HTTP_DOWNLOAD`, `FTP_DOWNLOAD`, and `ANY_DOWNLOAD`
  * request types, this is the file path to which the downloaded data should be saved.
  */
 public function __construct($url, $type = self::HTTP_GET, $downloadDestinationFp = null)
 {
     assert('is_cstring($url) && is_enum($type) && ' . '(!isset($downloadDestinationFp) || is_cstring($downloadDestinationFp))', vs(isset($this), get_defined_vars()));
     assert('CUrl::isValid($url, true)', vs(isset($this), get_defined_vars()));
     assert('!(($type == self::HTTP_DOWNLOAD || $type == self::FTP_DOWNLOAD || ' . '$type == self::ANY_DOWNLOAD) && !isset($downloadDestinationFp))', vs(isset($this), get_defined_vars()));
     // Find out the basic protocol from the request type.
     switch ($type) {
         case self::HTTP_GET:
         case self::HTTP_DOWNLOAD:
         case self::HTTP_POST:
         case self::HTTP_UPLOAD:
         case self::HTTP_PUT:
         case self::HTTP_DELETE:
         case self::HTTP_HEAD:
             $this->m_requestBasicProtocol = "http";
             break;
         case self::FTP_LIST:
         case self::FTP_DOWNLOAD:
         case self::FTP_UPLOAD:
             $this->m_requestBasicProtocol = "ftp";
             break;
         case self::ANY_DOWNLOAD:
             // Look into the URL.
             $objUrl = new CUrl(CUrl::ensureProtocol($url));
             $protocolFromUrl = $objUrl->normalizedProtocol();
             $this->m_requestBasicProtocol = self::basicProtocol($protocolFromUrl);
             break;
         default:
             assert('false', vs(isset($this), get_defined_vars()));
             break;
     }
     // If the URL does not indicate any protocol, which prevents it from being fully qualified, make the URL
     // indicate the protocol that was derived from the request type.
     $url = CUrl::ensureProtocol($url, $this->m_requestBasicProtocol);
     if (CDebug::isDebugModeOn()) {
         $objUrl = new CUrl($url);
         assert('$objUrl->hasProtocol()', vs(isset($this), get_defined_vars()));
         $basicProtocolFromUrl = self::basicProtocol($objUrl->normalizedProtocol());
         assert('CString::equals($basicProtocolFromUrl, $this->m_requestBasicProtocol)', vs(isset($this), get_defined_vars()));
     }
     $this->m_url = $url;
     $this->m_type = $type;
     $this->m_downloadDestinationFp = CFilePath::frameworkPath($downloadDestinationFp);
     $this->m_requestSummary = CMap::make();
     $this->m_responseHeaders = CArray::make();
     $this->m_responseHeadersLcKeys = CMap::make();
     $this->m_curl = curl_init();
     if (!is_resource($this->m_curl) || !CString::isEmpty(curl_error($this->m_curl))) {
         $this->m_hasError = true;
         $curlError = !is_resource($this->m_curl) ? "" : curl_error($this->m_curl);
         $this->m_errorMessage = CString::isEmpty($curlError) ? "cURL initialization failed." : $curlError;
         $this->finalize();
         return;
     }
 }
Exemplo n.º 2
0
 public function testEnsureProtocol()
 {
     $this->assertTrue(CUrl::ensureProtocol("www.example.com")->equals("http://www.example.com"));
     $this->assertTrue(CUrl::ensureProtocol("https://www.example.com")->equals("https://www.example.com"));
     $this->assertTrue(CUrl::ensureProtocol("ftp://www.example.com")->equals("ftp://www.example.com"));
     $this->assertTrue(CUrl::ensureProtocol("www.example.com/", "https")->equals("https://www.example.com/"));
 }
Exemplo n.º 3
0
 /**
  * Filters a string or a collection of strings according to the expected output type(s) and returns the output
  * value(s).
  *
  * @param  mixed $inputStringOrDecodedCollection The string to be filtered or the array or map containing the
  * strings to be filtered. If the parameter's value is a JSON-encoded string, the output value is going to be
  * either an array or map.
  * @param  reference $success **OUTPUT.** After the method is called, the value of this parameter tells whether
  * the filtering was successful.
  *
  * @return mixed The output value or a collection of values of the expected type(s) after having been put through
  * the filter.
  */
 public function filter($inputStringOrDecodedCollection, &$success)
 {
     assert('is_cstring($inputStringOrDecodedCollection) || is_collection($inputStringOrDecodedCollection)', vs(isset($this), get_defined_vars()));
     $success = true;
     if ($this->m_expectedType != self::CARRAY && $this->m_expectedType != self::CMAP) {
         // The expected output type is not a collection; the input value must be of string type.
         if (!is_cstring($inputStringOrDecodedCollection)) {
             $success = false;
             return oop_x($this->m_defaultValue);
         }
         $inputString = $inputStringOrDecodedCollection;
         if ($this->m_expectedType == self::BOOL || $this->m_expectedType == self::INT || $this->m_expectedType == self::FLOAT || $this->m_expectedType == self::EMAIL || $this->m_expectedType == self::URL || $this->m_expectedType == self::IP) {
             // Trim the input string on both sides from whitespace, including Unicode whitespace and control
             // characters.
             $trimmingSubjectRe = CUString::TRIMMING_AND_SPACING_NORM_SUBJECT_RE;
             $inputString = CRegex::remove($inputString, "/^({$trimmingSubjectRe})+|({$trimmingSubjectRe})+\\z/u");
         }
         // Pre-process the string for integer and floating-point types.
         $looksLikeHex;
         if ($this->m_expectedType == self::INT || $this->m_expectedType == self::FLOAT) {
             if (CString::startsWith($inputString, "+")) {
                 // Remove the plus sign.
                 $inputString = CString::substr($inputString, 1);
             }
             $looksLikeHex = CRegex::find($inputString, "/^-?0x/i");
             if ($this->m_allowLeadingZeros && !($this->m_expectedType == self::INT && $this->m_allowHex && $looksLikeHex)) {
                 // Remove any leading zeros (except for special cases).
                 $inputString = CRegex::replace($inputString, "/^(\\D*)0*(?!\\b)/", "\$1");
             }
             if ($this->m_allowComma) {
                 $inputString = CRegex::remove($inputString, "/,(?=\\d{3}\\b)/");
             }
         }
         // Validate and sanitize the value according to its expected type.
         if ($this->m_expectedType == self::BOOL) {
             if (!CRegex::find($inputString, "/^(1|true|yes|on|0|false|no|off)\\z/i")) {
                 $success = false;
                 return $this->m_defaultValue;
             }
             return CString::equals($inputString, "1") || CString::equalsCi($inputString, "true") || CString::equalsCi($inputString, "yes") || CString::equalsCi($inputString, "on");
         }
         if ($this->m_expectedType == self::INT) {
             $value;
             if (!($this->m_allowHex && $looksLikeHex)) {
                 // Regular.
                 if (!CRegex::find($inputString, "/^-?(?!0(?!\\b))\\d+\\z/")) {
                     $success = false;
                     return $this->m_defaultValue;
                 }
                 $value = CString::toInt($inputString);
             } else {
                 // Hex.
                 if (!CRegex::find($inputString, "/^-?0x[0-9A-F]+\\z/i")) {
                     $success = false;
                     return $this->m_defaultValue;
                 }
                 $value = CString::toIntFromHex($inputString);
             }
             if (isset($this->m_intValidMin) && $value < $this->m_intValidMin || isset($this->m_intValidMax) && $value > $this->m_intValidMax) {
                 $success = false;
                 return $this->m_defaultValue;
             }
             if (isset($this->m_intClampingMin) && $value < $this->m_intClampingMin) {
                 $value = $this->m_intClampingMin;
             }
             if (isset($this->m_intClampingMax) && $value > $this->m_intClampingMax) {
                 $value = $this->m_intClampingMax;
             }
             return $value;
         }
         if ($this->m_expectedType == self::FLOAT) {
             if (!CRegex::find($inputString, "/^-?(?!0(?!\\b))\\d*\\.?\\d+(e[\\-+]?\\d+)?\\z/i")) {
                 $success = false;
                 return $this->m_defaultValue;
             }
             $value = CString::toFloat($inputString);
             if (isset($this->m_floatValidMin) && $value < $this->m_floatValidMin || isset($this->m_floatValidMax) && $value > $this->m_floatValidMax) {
                 $success = false;
                 return $this->m_defaultValue;
             }
             if (isset($this->m_floatClampingMin) && $value < $this->m_floatClampingMin) {
                 $value = $this->m_floatClampingMin;
             }
             if (isset($this->m_floatClampingMax) && $value > $this->m_floatClampingMax) {
                 $value = $this->m_floatClampingMax;
             }
             return $value;
         }
         if ($this->m_expectedType == self::CSTRING) {
             $value = $inputString;
             if (!CString::isValid($value)) {
                 $success = false;
                 return $this->m_defaultValue;
             }
             if (!$this->m_keepAbnormalNewlines) {
                 $value = CString::normNewlines($value);
             }
             if (!$this->m_keepNonPrintable) {
                 if (!$this->m_keepTabsAndNewlines) {
                     $value = CRegex::remove($value, "/[\\x00-\\x1F\\x7F-\\xFF]/");
                 } else {
                     $value = CRegex::remove($value, "/[\\x00-\\x1F\\x7F-\\xFF](?<![\\x09\\x0A\\x0D])/");
                 }
             } else {
                 if (!$this->m_keepTabsAndNewlines) {
                     $value = CRegex::remove($value, "/[\\x09\\x0A\\x0D]/");
                 }
             }
             if (!$this->m_keepSideSpacing) {
                 $value = CString::trim($value);
             }
             if (!$this->m_keepExtraSpacing) {
                 $value = CString::normSpacing($value);
             }
             return $value;
         }
         if ($this->m_expectedType == self::CUSTRING) {
             $value = $inputString;
             if (!CUString::isValid($value)) {
                 $success = false;
                 return $this->m_defaultValue;
             }
             if (!$this->m_keepAbnormalNewlines) {
                 $value = CUString::normNewlines($value);
             }
             if (!$this->m_keepNonPrintable) {
                 if (!$this->m_keepTabsAndNewlines) {
                     $value = CRegex::remove($value, "/\\p{C}|\\p{Zl}|\\p{Zp}/u");
                 } else {
                     $value = CRegex::remove($value, "/\\p{C}(?<!\\x{0009}|\\x{000A}|\\x{000D})/u");
                 }
             } else {
                 if (!$this->m_keepTabsAndNewlines) {
                     $value = CRegex::remove($value, "/\\x{0009}|\\x{000A}|\\x{000D}|\\p{Zl}|\\p{Zp}/u");
                 }
             }
             if (!$this->m_keepSideSpacing) {
                 $value = CUString::trim($value);
             }
             if (!$this->m_keepExtraSpacing) {
                 $value = CUString::normSpacing($value);
             }
             return $value;
         }
         if ($this->m_expectedType == self::EMAIL) {
             $value = filter_var($inputString, FILTER_VALIDATE_EMAIL);
             if (!is_cstring($value)) {
                 $success = false;
                 return $this->m_defaultValue;
             }
             return $value;
         }
         if ($this->m_expectedType == self::URL) {
             $value = $inputString;
             if (!CUrl::isValid($value, $this->m_ignoreProtocolAbsence)) {
                 $success = false;
                 return $this->m_defaultValue;
             }
             if ($this->m_ignoreProtocolAbsence) {
                 $value = CUrl::ensureProtocol($value);
             }
             return $value;
         }
         if ($this->m_expectedType == self::IP) {
             $value = $inputString;
             $options = CBitField::ALL_UNSET;
             if (!$this->m_allowPrivateRange) {
                 $options |= CIp::DISALLOW_PRIVATE_RANGE;
             }
             if (!$this->m_allowReservedRange) {
                 $options |= CIp::DISALLOW_RESERVED_RANGE;
             }
             $isValid;
             if (!$this->m_ipV6 && !$this->m_ipV4OrV6) {
                 $isValid = CIp::isValidV4($value, $options);
             } else {
                 if (!$this->m_ipV4OrV6) {
                     $isValid = CIp::isValidV6($value, $options);
                 } else {
                     $isValid = CIp::isValidV4($value, $options) || CIp::isValidV6($value, $options);
                 }
             }
             if (!$isValid) {
                 $success = false;
                 return $this->m_defaultValue;
             }
             return $value;
         }
     } else {
         if ($this->m_expectedType == self::CARRAY) {
             if (!is_cstring($inputStringOrDecodedCollection) && !is_carray($inputStringOrDecodedCollection)) {
                 $success = false;
                 return oop_x($this->m_defaultValue);
             }
             $value;
             if (is_cstring($inputStringOrDecodedCollection)) {
                 // Assume JSON format for the input string.
                 $json = new CJson($inputStringOrDecodedCollection, $this->m_jsonStrictness);
                 $value = $json->decode($success);
                 if (!$success) {
                     return oop_x($this->m_defaultValue);
                 }
                 if (!is_carray($value)) {
                     $success = false;
                     return oop_x($this->m_defaultValue);
                 }
             } else {
                 $value = $inputStringOrDecodedCollection;
             }
             $value = self::recurseCollectionFiltering($value, $this->m_collectionInputFilters, $success, 0);
             if (!$success) {
                 return oop_x($this->m_defaultValue);
             }
             return $value;
         } else {
             if (!is_cstring($inputStringOrDecodedCollection) && !is_cmap($inputStringOrDecodedCollection)) {
                 $success = false;
                 return oop_x($this->m_defaultValue);
             }
             $value;
             if (is_cstring($inputStringOrDecodedCollection)) {
                 // Assume JSON format for the input string.
                 $json = new CJson($inputStringOrDecodedCollection, $this->m_jsonStrictness);
                 $value = $json->decode($success);
                 if (!$success) {
                     return oop_x($this->m_defaultValue);
                 }
                 if (!is_cmap($value)) {
                     $success = false;
                     return oop_x($this->m_defaultValue);
                 }
             } else {
                 $value = $inputStringOrDecodedCollection;
             }
             $value = self::recurseCollectionFiltering($value, $this->m_collectionInputFilters, $success, 0);
             if (!$success) {
                 return oop_x($this->m_defaultValue);
             }
             return $value;
         }
     }
 }