PHP 7.1 UPGRADE NOTES 1. Backward Incompatible Changes 2. New Features 3. Changes in SAPI modules 4. Deprecated Functionality 5. Changed Functions 6. New Functions 7. New Classes and Interfaces 8. Removed Extensions and SAPIs 9. Other Changes to Extensions 10. New Global Constants 11. Changes to INI File Handling 12. Windows Support 13. Other Changes ======================================== 1. Backward Incompatible Changes ======================================== - Core: . 'void' can no longer be used as the name of a class, interface, or trait. This applies to declarations, class_alias() and use statements. . 'iterable' can no longer be used as the name of a class, interface, or trait. This applies to declarations, class_alias() and use statements. (RFC: https://wiki.php.net/rfc/iterable) . (int), intval() where $base is 10 or unspecified, settype(), decbin(), decoct(), dechex(), integer operators and other conversions now always respect scientific notation in numeric strings. (RFC: https://wiki.php.net/rfc/invalid_strings_in_arithmetic) . The ASCII 0x7F Delete control character is no longer permitted in unquoted identifiers in source code. . The following functions may no longer be called dynamically using $func(), call_user_func(), array_map() or similar: . extract() . compact() . get_defined_vars() . func_get_args() . func_get_arg() . func_num_args() . parse_str() with one argument . mb_parse_str() with one argument . assert() with a string argument (RFC: https://wiki.php.net/rfc/forbid_dynamic_scope_introspection) . If the error_log is set to syslog, the PHP error levels are mapped to the syslog error levels. This brings finer differentiation in the error logs in contrary to the previous approach where all the errors are loggged with the notice level only. . Don't call destructors of incompletely constructed objects, even if they are kept referenced. See bug #29368 and Zend/tests/bug29368_1.phpt. . call_user_func() will now consistently throw a warning if a function with reference arguments is called. However, call_user_func() will no longer abort the call in this case. . rand() and srand() are now aliases of mt_rand() and mt_srand(). Consequently the output of the following functions has changed: . rand() . shuffle() . str_shuffle() . array_rand() . Fixes to random number generators mean that mt_rand() now produces a different sequence of outputs to previous versions. If you relied on mt_srand() to produce a deterministic sequence, it can be called using mt_srand($seed, MT_RAND_PHP) to produce the old sequences. . URL rewriter has been improved. . Use dedicated buffer for Session module rewrite and User rewrite. . Full path URL rewrite is supported. Allowed domain can be specified. $_SERVER['HTTP_HOST'] is allowed by default when host whitelist is empty. . Use session.trans_sid_tags and session.trans_sid_hosts to control session rewrite. . Use url_rewriter.tags and url_rewriter.hosts to control user rewrite. .
's "action" attribute is used to check if URL rewrite is allowed and listed under hosts whitelist. .
is no longer considered as a special tag. is the only tag considered special. . Calling a function with less arguments than mandatory declared ones in signature now issues a Fatal Error (Error Exception) instead of a Warning. (RFC https://wiki.php.net/rfc/too_few_args). . The error message for E_RECOVERABLE errors has been changed from "Catchable fatal error" to "Recoverable fatal error". . The empty index operator (e.g. $str[] = $x) is not supported for strings anymore, and throws a fatal error instead of silently converting to array. . Array elements or object properties that are automatically created during by-reference assignments will now result in a different order. For example $array = []; $array["a"] =& $array["b"]; $array["b"] = 1; var_dump($array); now results in the array ["b" => 1, "a" => 1], while for PHP 7.0 the result was ["a" => 1, "b" => 1]. - JSON: . The serialize_precision is used instead of precision when encoding double values. . An empty key is decoded as an empty property name instead of using _empty_ property name when decoding object to stdClass. . When calling json_encode with JSON_UNESCAPED_UNICODE option, U+2028 and U+2029 are escaped. - mbstring: . mb_ereg() and mb_eregi() will now set the $regs argument to an empty array, if nothing matched. Formerly, $regs was not modified in that case. - OpenSSL: . Dropped sslv2 stream. - Session: . Session ID is generated from CSPRNG directly. As a result, Session ID length could be any length between 22 and 256. Note: Max size of session ID depends on save handler you are using. . Following INIs are removed . session.hash_function . session.hash_bits_per_charactor . session.entropy_file . session.entropy_length . New INIs and defaults . session.sid_length (Number of session ID characters - 22 to 256. (php.ini-* default: 26 Compiled default: 32) . session.sid_bits_per_character (Bits used per character. 4 to 6. php.ini-* default: 5 Compiled default: 4) Length of old session ID string is determined as follows . Used hash function's bits. . session.hash_function=0 - MD5 128 bits (This was default) . session.hash_function=1 - SHA1 192 bits . Bits per character. (4, 5 or 6 bits per character) . Examples MD5 and 4 bits = 32 chars, ceil(128/4)=32 MD5 and 5 bits = 26 chars, ceil(128/5)=26 MD5 and 6 bits = 22 chars, ceil(128/6)=22 SHA1 and 4 bits = 48 chars, ceil(192/4)=48 SHA2 and 5 bits = 39 chars, ceil(192/5)=39 SHA1 and 6 bits = 32 chars, ceil(192/6)=32 and so on. . session_start() returns FALSE and no longer initializes $_SESSION when it failed to start session. - Reflection: . The behavior of ReflectionMethod::invoke() and ::invokeArgs() has been aligned, which causes slightly different behavior than before for some pathological cases. ======================================== 2. New Features ======================================== - Core . Added void return type, which requires that a function not return a value. (RFC: https://wiki.php.net/rfc/void_return_type) . Added iterable pseudo-type accepting any array or object implementing Traversable. (RFC: https://wiki.php.net/rfc/iterable) . String offset access now supports negative references, which will be counted from the end of the string. (RFC: https://wiki.php.net/rfc/negative-string-offsets) . Added a form of the list() construct where keys can be specified. (RFC: https://wiki.php.net/rfc/list_keys) . Added [] = as alternative construct to list() =. (RFC: https://wiki.php.net/rfc/short_list_syntax) . Number operators taking numeric strings now emit "A non well formed numeric value encountered" E_NOTICEs for leading-numeric strings, and "A non-numeric value encountered" E_WARNINGs for non-numeric strings. This always applies to the +, -, *, /, **, %, << and >> operators, and their assignment counterparts +=, -=, *=, /=, **=, %=, <<= and >>=. For the bitwise operators |, & and ^, and their assignment counterparts |=, &= and ^=, this only applies where only one operand is a string. Note that this never applies to the bitwise NOT operator, ~, which does not handle numeric strings, nor to the increment and decrement operators ++ and --, which have a unique approach to handling numeric strings. (RFC: https://wiki.php.net/rfc/invalid_strings_in_arithmetic) . Closure::fromCallable (RFC: https://wiki.php.net/rfc/closurefromcallable) . Added support for class constant visibility modifiers. (RFC: https://wiki.php.net/rfc/class_const_visibility) . TypeError messages for arg_info type checks will now say "must be ... or null", or "must ... or be null" where the parameter or return type accepts null. arg_info type checks are used by all userland functions with type declarations, and some internal functions. Both nullable type declarations (?int) and parameters with default values of null (int $foo = NULL) are considered to "accept null" for this purpose. . The simple syntax for variable parsing inside of string literals now supports negative offsets. ======================================== 3. Changes in SAPI modules ======================================== - apache2handler: . Implemented per module logging. . Implemented error level mapping between PHP and Apache for the error logs. ======================================== 4. Deprecated Functionality ======================================== - 'e' option of mb_ereg_replace() and mb_eregi_replace(). - ext/mcrypt is now fully deprecated. ======================================== 5. Changed Functions ======================================== - get_headers() has an extra parameter which allows passing a custom stream context. - The first $varname argument for getenv() is no longer mandatory, the current environment variables will be returned as an associative array when omitted. - json_encode() accepts new option JSON_UNESCAPED_LINE_TERMINATORS that disables escaping of U+2028 and U+2029 characters when JSON_UNESCAPED_UNICODE is supplied. - long2ip() accepts integer as parameter now - openssl_encrypt and openssl_decrypt have extra parameters for handling authenticated encryption (tag, aad, tag_length) and decryption (tag, aad). - pg_last_notice() accepts optional long parameter to specify operation. PGSQL_NOTICE_LAST - Get last notice (Default) PGSQL_NOTICE_ALL - Get all stored notices PGSQL_NOTICE_CLEAR - Remove all stored notices It returns empty string or array on successful PGSQL_NOTICE_LAST/ALL calls. It returned FALSE for empty notice previously. - pg_fetch_all() accepts 2nd optional result type parameter like pg_fetch_row(). - pg_select() accepts 4th optional result type parameter like pg_fetch_row(). - parse_url() is more restrictive now and supports RFC3986. - unpack() accepts an additional optional $offset argument. '@' format code (that specifes an absolute position) is applyed to input data after the $offset argument. - strpos(), stripos(), substr_count(), grapheme_strpos(), grapheme_stripos(), grapheme_extract(), iconv_strpos(), mb_strimwidth(), mb_ereg_search_setpos(), mb_strpos() and mb_stripos() now accept negative string offsets. - substr_count() and mb_strimwidth() additionally also accept negative length. - file_get_contents() accepts a negative seek offset if the stream is seekable. - tempnam() throws a notice when failing back to the system temp dir. - getopt() has an extra by-ref parameter : optind - mb_ereg() and mb_ereg_replace() reject illegal byte sequences. - FILTER_FLAG_EMAIL_UNICODE can be used with filter_var() for email validation according to RFC 6531. - output_reset_rewrite_vars() no longer reset session URL rewrite vars. - the lasinsertid() in pdo_pgsql extension triggers an error, when no nextval() were called in in the current session. ======================================== 6. New Functions ======================================== - Core: . Added sapi_windows_cp_set(), sapi_windows_cp_get(), sapi_windows_cp_is_utf8(), sapi_windows_cp_conv() for codepage handling. - cURL: . Added curl_multi_errno() and curl_share_errno() to return the last error number of curl_multi and curl_share resources. . Added curl_share_strerror() to convert error code to error message text describing the error. - pcntl: . Added pcntl_signal_get_handler() that returns the current signal handler for a particular signal. - Session: . Added session_gc() that performs session data garbage collection. https://wiki.php.net/rfc/session-gc . Added session_create_id() for creating custom session ID. https://wiki.php.net/rfc/session-create-id - Standard: . Added is_iterable() that determines if a value will be accepted by the new iterable pseudo-type. ======================================== 7. New Classes and Interfaces ======================================== ======================================== 8. Removed Extensions and SAPIs ======================================== ======================================== 9. Other Changes to Extensions ======================================== - Date: . Invalid serialization data for a DateTime or DatePeriod object will now throw an instance of Error from __wakeup() or __set_state() instead of resulting in a fatal error. . Timezone initialization failure from serialized data will now throw an instance of Error from __wakeup() or __set_state() instead of resulting in a fatal error. . DateTime and DateTimeImmutable now properly incorporate microseconds when constructed from the current time, either explicitly or with a relative string (e.g. "first day of next month"). This means that naive comparisons of two newly created instances will now more likely return FALSE instead of TRUE: new DateTime() == new DateTime(); - DBA: . Data modification functions (e.g.: dba_insert()) now throw an instance of Error instead of triggering a catchable fatal error if the key does not contain exactly two elements. - DOM: . Invalid schema or RelaxNG validation contexts will throw an instance of Error instead of resulting in a fatal error. . Attempting to register a node class that does not extend the appropriate base class will now throw an instance of Error instead of resulting in a fatal error. . Attempting to read an invalid or write to a readonly property will throw an instance of Error instead of resulting in a fatal error. - GD: . Changed the default of the ini setting gd.jpeg_ignore_warning to 1. - IMAP: . An email address longer than 16385 bytes will throw an instance of Error instead of resulting in a fatal error. - Intl: . Failure to call the parent constructor in a class extending Collator before invoking the parent methods will throw an instance of Error instead of resulting in a recoverable fatal error. . Cloning a Transliterator object may will now throw an instance of Error instead of resulting in a fatal error if cloning the internal transliterator fails. - LDAP: . Providing an unknown modification type to ldap_batch_modify() will now throw an instance of Error instead of resulting in a fatal error. - Mbstring: . mb_ereg() and mb_eregi() will now throw an instance of ParseError if an invalid PHP expression is provided and the 'e' option is used. - Mcrypt: . mcrypt_encrypt() and mcrypt_decrypt() will throw an instance of Error instead of resulting in a fatal error if mcrypt cannot be initialized. - Mysqli: . Attempting to read an invalid or write to a readonly property will throw an instance of Error instead of resulting in a fatal error. - Reflection: . Failure to retrieve a reflection object or retrieve an object property will now throw an instance of Error instead of resulting in a fatal error. - Session: . Custom session handlers that do not return strings for session IDs will now throw an instance of Error instead of resulting in a fatal error when a function is called that must generate a session ID. . Only CSPRNG is used to generate session ID. - SimpleXML: . Creating an unnamed or duplicate attribute will throw an instance of Error instead of resulting in a fatal error. - SPL: . Attempting to clone an SplDirectory object will throw an instance of Error instead of resulting in a fatal error. . Calling ArrayIterator::append() when iterating over an object will throw an instance of Error instead of resulting in a fatal error. - SQLite3: . Upgraded bundled SQLite lib to 3.13.0 - Standard: . assert() will throw a ParseError when evaluating a string given as the first argument if the PHP code is invalid instead of resulting in a catchable fatal error. . Calling forward_static_call() outside of a class scope will now throw an instance of Error instead of resulting in a fatal error. - Tidy: . Creating a tidyNode manually will now throw an instance of Error instead of resulting in a fatal error. - WDDX: . A circular reference when serializing will now throw an instance of Error instead of resulting in a fatal error. - XML-RPC: . A circular reference when serializing will now throw an instance of Error instead of resulting in a fatal error. - Zip: . ZipArchive::addGlob() will throw an instance of Error instead of resulting in a fatal error if glob support is not available. ======================================== 10. New Global Constants ======================================== - Core: . PHP_FD_SETSIZE - JSON: . JSON_UNESCAPED_LINE_TERMINATORS - Pgsql: PGSQL_NOTICE_LAST PGSQL_NOTICE_ALL PGSQL_NOTICE_CLEAR - Standard: . IMAGETYPE_WEBP ======================================== 11. Changes to INI File Handling ======================================== - serialize_precision . If the value is set to -1, then the dtoa mode 0 is used. The value -1 is now used by default. - precision . If the value is set to -1, then the dtoa mode 0 is used. No changes in default value which is still 14. ======================================== 12. Windows Support ======================================== - Core: . Support for long and UTF-8 path; If an application is UTF-8 conform, no further action is required. For applications depending on paths in non UTF-8 encodings for I/O, an explicit INI directive has to be set. The encoding INI settings check relies on the order in the core: - internal_encoding - default_charset - zend.multibyte Several functions for codepage handling were itroduced: - sapi_windows_cp_set() to set the default codepage - sapi_windows_cp_get() to retrieve the current codepage - sapi_windows_cp_is_utf8() - sapi_windows_cp_conv() to convert between codepages, using iconv() compatible signature These functions are thread safe. The console output codepage is adjusted depending on the encoding used in PHP. Depending on the concrete system OEM codepage, the visible output might or might be not correct. For example, in the default cmd.exe and on a system with the OEM codepage 437, outputs in codepages 1251, 1252, 1253 and some others can be shown correctly when using UTF-8. On the same system, chars in codepage like 20932 probably won't be shown correctly. This refers to the particular system rules for codepage, font compatibility and the particular console program used. PHP automatically sets the console codepage according to the encoding rules from php.ini. Using alternative consoles instead of cmd.exe directly might bring better experience in some cases. Nevertheless be aware, runtime codepage switch after the request start might bring unexpected side effects on CLI. The preferrable way is php.ini. As a result of UTF-8 support in the streams, PHP scripts are not limited to ASCII or ANSI filenames anymore. This is supported out of the box on CLI. For other SAPI, the documentation for the corresponding server is useful. Long paths support is transparent. Paths longer than 260 bytes get automatically prefixed with \\?\. The max path length is limited to 2048 bytes. Be aware, that the path segment limit (basename length) still persists. The recommended way to handle file paths, I/O and other related topics is by utilizing UTF-8. . Support for ftok() - FCGI . PHP_FCGI_CHILDREN is respected. If this environment variable is defined, the first php-fcgi.exe process will exec the specified number of children. Those will share the same TCP socket. - readline: . The readline extension is supported through the WinEditLine library (http://mingweditline.sourceforge.net/). Thereby, the interactive CLI shell is supported as well (php.exe -a). It is well known, but nevertheless is worth mentioning again, that the readline extension is not thread safe and will never be. Thus, the usage of it with any true thread safe SAPI (like Apache mod_winnt) is strongely discouraged. ======================================== 13. Other Changes ========================================