Unserialize function unserialize error

(PHP 4, PHP 5, PHP 7, PHP 8)

(PHP 4, PHP 5, PHP 7, PHP 8)

unserialize
Creates a PHP value from a stored representation

Description

unserialize(string $data, array $options = []): mixed

unserialize() takes a single serialized variable and
converts it back into a PHP value.

Warning

Do not pass untrusted user input to unserialize() regardless
of the options value of allowed_classes.
Unserialization can result in code being loaded and executed due to object
instantiation and autoloading, and a malicious user may be able to exploit
this. Use a safe, standard data interchange format such as JSON (via
json_decode() and json_encode()) if
you need to pass serialized data to the user.

If you need to unserialize externally-stored serialized data, consider using
hash_hmac() for data validation. Make sure data is
not modified by anyone but you.

Parameters

data

The serialized string.

If the variable being unserialized is an object, after successfully
reconstructing the object PHP will automatically attempt to call the
__unserialize() or __wakeup() methods (if one exists).

Note:
unserialize_callback_func directive

It’s possible to set a callback-function which will be called,
if an undefined class should be instantiated during unserializing.
(to prevent getting an incomplete object «__PHP_Incomplete_Class».)
Use your php.ini, ini_set() or .htaccess
to define unserialize_callback_func.
Everytime an undefined class should be instantiated, it’ll be called. To disable this feature just
empty this setting.

options

Any options to be provided to unserialize(), as an
associative array.

Valid options

Name Type Description
allowed_classes mixed
Either an array of class names which should be
accepted, false to accept no classes, or true to accept all
classes. If this option is defined and
unserialize() encounters an object of a class
that isn’t to be accepted, then the object will be instantiated as
__PHP_Incomplete_Class instead.


Omitting this option is the same as defining it as true: PHP
will attempt to instantiate objects of any class.
max_depth int
The maximum depth of structures permitted during unserialization,
and is intended to prevent stack overflows. The default depth limit
is 4096 and can be disabled by setting
max_depth to 0.

Return Values

The converted value is returned, and can be a bool,
int, float, string,
array or object.

In case the passed string is not unserializeable, false is returned and
E_NOTICE is issued.

Errors/Exceptions

Objects may throw Throwables in their unserialization handlers.

Changelog

Version Description
7.4.0 Added the max_depth element of
options to set the maximum depth of structures permitted during unserialization.
7.1.0 The allowed_classes element of
options) is now strictly typed, i.e. if anything
other than an array or a bool is given,
unserialize() returns false and issues an
E_WARNING.

Examples

Example #1 unserialize() example


<?php
// Here, we use unserialize() to load session data to the
// $session_data array from the string selected from a database.
// This example complements the one described with serialize().
$conn = odbc_connect("webdb", "php", "chicken");
$stmt = odbc_prepare($conn, "SELECT data FROM sessions WHERE id = ?");
$sqldata = array($_SERVER['PHP_AUTH_USER']);
if (!
odbc_execute($stmt, $sqldata) || !odbc_fetch_into($stmt, $tmp)) {
// if the execute or fetch fails, initialize to empty array
$session_data = array();
} else {
// we should now have the serialized data in $tmp[0].
$session_data = unserialize($tmp[0]);
if (!
is_array($session_data)) {
// something went wrong, initialize to empty array
$session_data = array();
}
}
?>

Example #2 unserialize_callback_func example


<?php
$serialized_object
='O:1:"a":1:{s:5:"value";s:3:"100";}';ini_set('unserialize_callback_func', 'mycallback'); // set your callback_functionfunction mycallback($classname)
{
// just include a file containing your class definition
// you get $classname to figure out which class definition is required
}
?>

Notes

Warning

false is returned both in the case of an error and if unserializing
the serialized false value. It is possible to catch this special case by
comparing data with
serialize(false) or by catching the issued
E_NOTICE.

See Also

  • json_encode() — Returns the JSON representation of a value
  • json_decode() — Decodes a JSON string
  • hash_hmac() — Generate a keyed hash value using the HMAC method
  • serialize() — Generates a storable representation of a value
  • Autoloading Classes
  • unserialize_callback_func
  • unserialize_max_depth
  • __wakeup()
  • __serialize()
  • __unserialize()

me+phpnet at unreal4u dot com

5 years ago


Just some reminder which may save somebody some time regarding the `$options` array:

Say you want to be on the safe side and not allow any objects to be unserialized... My first thought was doing the following:

<?php
$lol
= unserialize($string, false);
// This will generate:
// Warning: unserialize() expects parameter 2 to be array, boolean given
?>

The correct way of doing this is the following:
<?php
$lol
= unserialize($string, ['allowed_classes' => false]);
?>

Hope it helps somebody!


karsten at dambekalns dot de

2 years ago


Keep in mind that the allowed_classes does not use inheritance, i.e. allowing an interface is not possible and sub-classes won't pass the check. See https://3v4l.org/tdHfl

hadley8899 at gmail dot com

3 years ago


For the people who are getting the error

PHP Notice:  unserialize(): Error at offset 191 of 285 bytes in ...

and are getting the data from a database, Make sure that you have the database set the the correct encoding, I had the database set as latin1_swedish_ci and all of the data looked perfect, Infact when i copied it into a online unserialize it worked fine. I changed the collation to utf8mb4_unicode_ci and all worked fine.


daniel at fourstaples dot com

12 years ago


Here's a simple function to get the class of a serialized string (that is, the type of object that will be returned if it's unserialized):

<?php
function get_serial_class($serial) {
   
$types = array('s' => 'string', 'a' => 'array', 'b' => 'bool', 'i' => 'int', 'd' => 'float', 'N;' => 'NULL');$parts = explode(':', $serial, 4);
    return isset(
$types[$parts[0]]) ? $types[$parts[0]] : trim($parts[2], '"');
}
?>

I use this when saving a serialized object to a cookie, to make sure it is the right type when I go to unserialize it.

The type names are the same format/case as you would see if you did a var_dump().


ErnestV

9 years ago


Just a note - if the serialized string contains a reference to a class that cannot be instantiated (e.g. being abstract) PHP will immediately die with a fatal error. If the unserialize() statement is preceded with a '@' to avoid cluttering the logs with warns or notices there will be absolutely no clue as to why the script stopped working. Cost me a couple of hours...

chris at pollett dot org

7 years ago


When you serialize an object of a class from a particular namespace, the namespace is recorded as part of the serialization. If you decide to change this namespace's name, it can be hard to read in old serialized objects. I.e., suppose you had serialized an object of type fooA, you change the namespace of your project to goo but otherwise leave the class definition of A unchanged. You would like to be able to unserialize the object as gooA, instead unserialization will only create a partial object. To fix this in the case where you don't have nested objects in your class definition, you can use the following simple rename function:
/**
* Used to change the namespace of a serialized php object (assumes doesn't
* have nested subobjects)
*
* @param string $class_name new fully qualified name with namespace
* @param string $object_string serialized object
*
* @return string serialized object with new name
*/
function renameSerializedObject($class_name, $object_string)
{
    /*  number of digits in the length of name of the object needs to be
        less than 12 digits (probably more like 4) for this to work.
    */
    $name_length = intval(substr($object_string, 2, 14));
    $name_space_info_length = strlen("O:".$name_length.":") +
        $name_length + 2; // 2 for quotes;
    $object_string = 'O:' .
        strlen($class_name) . ':"'. $class_name.'"' .
        substr($object_string, $name_space_info_length);
    return $object_string;
}

Ray.Paseur often uses Gmail

9 years ago


In the Classes and Objects docs, there is this: In order to be able to unserialize() an object, the class of that object needs to be defined.

Prior to PHP 5.3, this was not an issue.  But after PHP 5.3 an object made by SimpleXML_Load_String() cannot be serialized.  An attempt to do so will result in a run-time failure, throwing an exception.  If you store such an object in $_SESSION, you will get a post-execution error that says this:

Fatal error: Uncaught exception 'Exception' with message 'Serialization of 'SimpleXMLElement' is not allowed' in [no active file]:0 Stack trace: #0 {main} thrown in [no active file] on line 0

The entire contents of the session will be lost.  Hope this saves someone some time!

<?php // RAY_temp_ser.php
error_reporting(E_ALL);
session_start();
var_dump($_SESSION);
$_SESSION['hello'] = 'World';
var_dump($_SESSION);// AN XML STRING FOR TEST DATA
$xml = '<?xml version="1.0"?>
<families>
  <parent>
    <child index="1" value="Category 1">Child One</child>
  </parent>
</families>'
;// MAKE AN OBJECT (GIVES SimpleXMLElement)
$obj = SimpleXML_Load_String($xml);// STORE THE OBJECT IN THE SESSION
$_SESSION['obj'] = $obj;


arbie samong

13 years ago


__PHP_Incomplete_Class Object Demystified

1. First take note of the output. A simple example:

__PHP_Incomplete_Class Object (

[__PHP_Incomplete_Class_Name] => SomeObject1

[obj1property1] => somevalue1 [obj1property2] => __PHP_Incomplete_Class Object ( [__PHP_Incomplete_Class_Name] => SomeObject2 [obj2property1] => somevalue1 [obj2property2] => Array (

['key1'] => somevalue3, ['key2'] => somevalue4 ) ) )

2. We analyze this and break it down.

__PHP_Incomplete_Class Object tells you there is an object that needs to be declared somehow.

__PHP_Incomplete_Class_Name simply tells you the expected class name. It is just one of the properties for now.

So we have:

a) an unknown object that has a class name SomeObject1 (first class)

b) it has 2 properties, namely obj1property1 and obj2property2

c) obj2property2 is itself an object whose class name is SomeObject2 (the second class)

d) SomeObject2 has two properties, obj2property1 and obj2property2

e) obj2property2 is an array that contains two elements

3. Now that we have an idea of the structure, we shall create class definitions based from it. We will just create properties for now, methods are not required as a minimum.

<?php

class SomeObject1 {

        public
$obj1property1;

        public
$obj1property2;

}

class
SomeObject2 {

        public
$obj2property1;

        public
$obj2property2;

}

?>



4. Have that accessible to your script and it will solve the __PHP_Incomplete_Class Object problem as far as the output is concerned. Now you will have:

SomeObject1 ( [obj1property1] => somevalue1 [obj1property2] => SomeObject2 ( [obj2property1] => somevalue1 [obj2property2] => Array ( ['key1'] => somevalue3, ['key2'] => somevalue4 ) ) )

As you will notice, __PHP_Incomplete_Class Object is gone and replaced by the class name. The property __PHP_Incomplete_Class_Name is also removed.

5. As for the array property obj2property2, we can directly access that and just assume that it is an array and loop through it:

<?php
// this will be SomeObject1

$data = unserialize($serialized_data);
// this will be SomeObject2

$data2 = $data->obj1property2();

foreach(

$data2->obj2property2 as $key => $value):

         print
$key.' : '. $value .'<br>';

endforeach;
?>



Outputs:

key1 : somevalue3

key2 : somevalue4

That's it. You can add more methods on the class declarations for the given properties, provided you keep your original output as basis for the data types.


m.m.j.kronenburg

6 years ago


You can use the following code to use the php 7 unserialize function in php 5.3 and upwards. This adds the $option argument.

<?phpnamespace
{
/**
* PHP 7 unserialize function for PHP 5.3 upwards.
* Added the $option argument (allowed_classes).
* See php unserialize manual for more detail.
**/
function php7_unserialize($str, $options = array())
{
  if(
version_compare(PHP_VERSION, '7.0.0', '>='))
  { return
unserialize($str, $options); }$allowed_classes = isset($options['allowed_classes']) ?
   
$options['allowed_classes'] : true;
  if(
is_array($allowed_classes) || !$allowed_classes)
  {
   
$str = preg_replace_callback(
     
'/(?=^|:)(O|C):d+:"([^"]*)":(d+):{/',
      function(
$matches) use ($allowed_classes)
      {
        if(
is_array($allowed_classes) &&
         
in_array($matches[2], $allowed_classes))
        { return
$matches[0]; }
        else
        {
          return
$matches[1].':22:"__PHP_Incomplete_Class":'.
            (
$matches[3] + 1).
           
':{s:27:"__PHP_Incomplete_Class_Name";'.
           
serialize($matches[2]);
        }
      },
     
$str
   
);
  }
  unset(
$allowed_classes);
  return
unserialize($str);
}

}

// namespacenamespace my_name_space
{
 
/**
   * Use the new php7 unserialize in your namespace without
   * renaming all unserialize(...) function calls to
   * php7_unserialize(...).
   **/
 
function unserialize($str, $options = array())
  { return
php7_unserialize($str, $options); }
}
?>


chris AT cmbuckley DOT co DOT uk

14 years ago


As mentioned in the notes, unserialize returns false in the event of an error and for boolean false. Here is the first solution mentioned, without using error handling:

<?php
function isSerialized($str) {
    return (
$str == serialize(false) || @unserialize($str) !== false);
}
var_dump(isSerialized('s:6:"foobar";')); // bool(true)
var_dump(isSerialized('foobar'));        // bool(false)
var_dump(isSerialized('b:0;'));          // bool(true)
?>


w dot laurencine at teknoa dot net

13 years ago


When dealing with a string which contain "r", it seems that the length is not evaluated correctly. The following solves the problem for me :

<?php
// remove the r caracters from the $unserialized string
$unserialized = str_replace("r","",$unserialized);// and then unserialize()
unserialize($unserialized);
?>


chris at colourlovers dot com

11 years ago


Anyone having trouble serializing data with SimpleXMLElement objects stored within it, check this out:

This will traverse $data looking for any children which are instances of SimpleXMLElement, and will run ->asXML() on them, turning them into a string and making them serializable. Other data will be left alone.

<?php
function exportNestedSimpleXML($data) {
    if (
is_scalar($data) === false) {
        foreach (
$data as $k => $v) {
            if (
$v instanceof SimpleXMLElement) {
               
$v = str_replace(" ","r",$v->asXML());
            } else {
               
$v = exportNestedSimpleXML($v);
            }

            if (

is_array($data)) {
               
$data[$k] = $v;
            } else if (
is_object($data)) {
               
$data->$k = $v;
            }
        }
    }

    return

$data;
}
$data = array (
   
"baz" => array (
       
"foo" => new stdClass(),
       
"int" => 123,
       
"str" => "asdf",
       
"bar" => new SimpleXMLElement('<?xml version="1.0" encoding="UTF-8"?><foo>bar</foo>'),
    )
);
var_dump($data);
/*array(1) {
  ["baz"]=>
  array(4) {
    ["foo"]=>
    object(stdClass)#3 (0) {
    }
    ["int"]=>
    int(123)
    ["str"]=>
    string(4) "asdf"
    ["bar"]=>
    object(SimpleXMLElement)#4 (1) {
      [0]=>
      string(3) "bar"
    }
  }
}*/
var_dump(exportNestedSimpleXML($data));
/*array(1) {
  ["baz"]=>
  array(4) {
    ["foo"]=>
    object(stdClass)#3 (0) {
    }
    ["int"]=>
    int(123)
    ["str"]=>
    string(4) "asdf"
    ["bar"]=>
    string(54) "<?xml version="1.0" encoding="UTF-8"?>
<foo>bar</foo>
"
  }
}
*/
?>


double at dumpit dot com

16 years ago


This little function will check whether the serialized string is well formed.

PHP < 6 because i'd heard changes will be made in this php-intern function,
maybe it could be edited easy for it.

<?phpfunction wd_check_serialization( $string, &$errmsg )
{
$str = 's';
   
$array = 'a';
   
$integer = 'i';
   
$any = '[^}]*?';
   
$count = 'd+';
   
$content = '"(?:\";|.)*?";';
   
$open_tag = '{';
   
$close_tag = '}';
   
$parameter = "($str|$array|$integer|$any):($count)" . "(?:[:]($open_tag|$content)|[;])";           
   
$preg = "/$parameter|($close_tag)/";
    if( !
preg_match_all( $preg, $string, $matches ) )
    {           
       
$errmsg = 'not a serialized string';
        return
false;
    }   
   
$open_arrays = 0;
    foreach(
$matches[1] AS $key => $value )
    {
        if( !empty(
$value ) && ( $value != $array xor $value != $str xor $value != $integer ) )
        {
           
$errmsg = 'undefined datatype';
            return
false;
        }
        if(
$value == $array )
        {
           
$open_arrays++;                               
            if(
$matches[3][$key] != '{' )
            {
               
$errmsg = 'open tag expected';
                return
false;
            }
        }
        if(
$value == '' )
        {
            if(
$matches[4][$key] != '}' )
            {
               
$errmsg = 'close tag expected';
                return
false;
            }
           
$open_arrays--;
        }
        if(
$value == $str )
        {
           
$aVar = ltrim( $matches[3][$key], '"' );
           
$aVar = rtrim( $aVar, '";' );
            if(
strlen( $aVar ) != $matches[2][$key] )
            {
               
$errmsg = 'stringlen for string not match';
                return
false;
            }
        }
        if(
$value == $integer )
        {
            if( !empty(
$matches[3][$key] ) )
            {
               
$errmsg = 'unexpected data';
                return
false;
            }
            if( !
is_integer( (int)$matches[2][$key] ) )
            {
               
$errmsg = 'integer expected';
                return
false;
            }
        }
    }       
    if(
$open_arrays != 0 )
    {
       
$errmsg = 'wrong setted arrays';
        return
false;
    }
    return
true;
}
?>


BenBE at omorphia dot de

15 years ago


When trying to serialize or unserialize recursive arrays or otherwise linked data you might find the undocumented R data type quite useful.

If you want a array like the one produced with
<?
$a = array();
$a[0] =& $a;
?>
serialized you can store it using a string simular to this one:
<?
$a = unserialize("a:1:{i:0;R:1;}");
?>

Both sources will make $a hold an array that self-references itself in index 0.

The argument for R is the index of the created sub-variable of the serialize-string beginning with 1.


Are Pedersen

16 years ago


Be aware that if useing serialize/unserialize in a serverfarm with both 32bit and 64bit servers you can get unexpected results.

Ex: if you serialize an integer with value of 2147483648 on a 64bit system and then unserialize it on a 32bit system you will get the value -2147483648 instead. This is because an integer on 32bit cannot be above 2147483647 so it wraps.


OscarZarrus

3 months ago


For those who are looking for an efficient solution for handling controversial "FALSE", they can use this function which in case of non-unserializable string, instead of a "FALSE", throws an Exception. Vice versa it returns the unserialized variable.

<?php

   
/**

     * @param string $serializedString

     * @param array $options

     * @return mixed

     * @throws Exception

     */

   
function UnSerialize(string $serializedString, array $options = []) {

       
$_unserialized = @unserialize($serializedString, $options);

        if (
$serializedString === serialize(false) || $_unserialized !== false){

            return
$_unserialized;

        }

        throw new
Exception("Non-unserializable string");

    }

?>

Chris Hayes (chris at hypersites dot com)

18 years ago


In reply to the earlier post about having to include object definitions *before* using unserialize.  There is a workaround for this.

When an object is serialized, the first bit of the string is actually the name of the class.  When an unknown object is unserialized, this is maintained as a property.  So if you serialize it again, you get back the exact same string as if you'd serialized the original object.  Basically, to cut to the point...

If you use

$_SESSION['my_object'] = unserialize(serialize($_SESSION['my_object']))

then you get back an object of the correct type, even if the session had originally loaded it as an object of type stdClass.


suman dot jis at gmail dot com

10 years ago


I was getting unserialize()  Error at offset error.

If you face similar problem  then use the following procedure

$auctionDetails = preg_replace('!s:(d+):"(.*?)";!se', "'s:'.strlen('$2').':"$2";'", $dataArr[$i]['auction_details'] );
$auctionDetails = unserialize($auctionDetails);


Anonymous

3 years ago


If serialize() is the answer, you're almost certainly asking the wrong question.

JSON is widely available. The only thing it does not do, is the very thing that makes serialization immensely dangerous. All it takes is a crafty hacker to pass a crafted payload to a supposedly 'secured' serialize call, for a database driver to be overwritten with malicious code, for example.

Recreate the object. Normally. With actual data, and a source file, not with serialize. To do otherwise is laziness bordering on malice.


aderyn at nowhere dot tld

19 years ago


A quick note:
If you store a serialized object in a session, you have to include the class _before_ you initialize (session_start()) the session.

MBa

11 years ago


To check if a string is serialized:

$blSerialized=(@unserialize($sText)||$sText=='b:0;');


walf

11 years ago


a replacement for unserialize that returns whether it worked and populates the unserialized variable by reference:
<?php
function funserialize($serialized, &$into) {
    static
$sfalse;
    if (
$sfalse === null)
       
$sfalse = serialize(false);
   
$into = @unserialize($serialized);
    return
$into !== false || rtrim($serialized) === $sfalse;//whitespace at end of serialized var is ignored by PHP
}$s_foo = 'b:0;';
var_dump(funserialize($s_foo, $foo), $foo);$s_bar = 'bar';
var_dump(funserialize($s_bar, $bar), $bar);$s_foo = 'a:0:{};';
var_dump(funserialize($s_foo, $foo), $foo);?>
gives:

bool(true)
bool(false)

bool(false)
bool(false)

bool(true)
array(0) {
}


Fagzal

12 years ago


To all who have problem with quoting and slashes when storing serialized data in MySQL: you are probably doing it wrong.

Use e.g. PDO with placeholders and the blob column type, and it will Just Work.


unserialize() [function.unserialize]: Error at offset was dues to invalid serialization data due to invalid length

Quick Fix

What you can do is is recalculating the length of the elements in serialized array

You current serialized data

$data = 'a:10:{s:16:"submit_editorial";b:0;s:15:"submit_orig_url";s:13:"www.bbc.co.uk";s:12:"submit_title";s:14:"No title found";s:14:"submit_content";s:12:"dnfsdkfjdfdf";s:15:"submit_category";i:2;s:11:"submit_tags";s:3:"bbc";s:9:"submit_id";b:0;s:16:"submit_subscribe";i:0;s:15:"submit_comments";s:4:"open";s:5:"image";s:19:"C:fakepath100.jpg";}';

Example without recalculation

var_dump(unserialize($data));

Output

Notice: unserialize() [function.unserialize]: Error at offset 337 of 338 bytes

Recalculating

$data = preg_replace('!s:(d+):"(.*?)";!e', "'s:'.strlen('$2').':"$2";'", $data);
var_dump(unserialize($data));

Output

array
  'submit_editorial' => boolean false
  'submit_orig_url' => string 'www.bbc.co.uk' (length=13)
  'submit_title' => string 'No title found' (length=14)
  'submit_content' => string 'dnfsdkfjdfdf' (length=12)
  'submit_category' => int 2
  'submit_tags' => string 'bbc' (length=3)
  'submit_id' => boolean false
  'submit_subscribe' => int 0
  'submit_comments' => string 'open' (length=4)
  'image' => string 'C:fakepath100.jpg' (length=17)

Recommendation .. I

Instead of using this kind of quick fix … i»ll advice you update the question with

  • How you are serializing your data

  • How you are Saving it ..

================================ EDIT 1 ===============================

The Error

The Error was generated because of use of double quote " instead single quote ' that is why C:fakepath100.png was converted to C:fakepath100.jpg

To fix the error

You need to change $h->vars['submitted_data'] From (Note the singe quite ' )

Replace

 $h->vars['submitted_data']['image'] = "C:fakepath100.png" ;

With

 $h->vars['submitted_data']['image'] = 'C:fakepath100.png' ;

Additional Filter

You can also add this simple filter before you call serialize

function satitize(&$value, $key)
{
    $value = addslashes($value);
}

array_walk($h->vars['submitted_data'], "satitize");

If you have UTF Characters you can also run

 $h->vars['submitted_data'] = array_map("utf8_encode",$h->vars['submitted_data']);

How to detect the problem in future serialized data

  findSerializeError ( $data1 ) ;

Output

Diffrence 9 != 7
    -> ORD number 57 != 55
    -> Line Number = 315
    -> Section Data1  = pen";s:5:"image";s:19:"C:fakepath100.jpg
    -> Section Data2  = pen";s:5:"image";s:17:"C:fakepath100.jpg
                                            ^------- The Error (Element Length)

findSerializeError Function

function findSerializeError($data1) {
    echo "<pre>";
    $data2 = preg_replace ( '!s:(d+):"(.*?)";!e', "'s:'.strlen('$2').':"$2";'",$data1 );
    $max = (strlen ( $data1 ) > strlen ( $data2 )) ? strlen ( $data1 ) : strlen ( $data2 );

    echo $data1 . PHP_EOL;
    echo $data2 . PHP_EOL;

    for($i = 0; $i < $max; $i ++) {

        if (@$data1 {$i} !== @$data2 {$i}) {

            echo "Diffrence ", @$data1 {$i}, " != ", @$data2 {$i}, PHP_EOL;
            echo "t-> ORD number ", ord ( @$data1 {$i} ), " != ", ord ( @$data2 {$i} ), PHP_EOL;
            echo "t-> Line Number = $i" . PHP_EOL;

            $start = ($i - 20);
            $start = ($start < 0) ? 0 : $start;
            $length = 40;

            $point = $max - $i;
            if ($point < 20) {
                $rlength = 1;
                $rpoint = - $point;
            } else {
                $rpoint = $length - 20;
                $rlength = 1;
            }

            echo "t-> Section Data1  = ", substr_replace ( substr ( $data1, $start, $length ), "<b style="color:green">{$data1 {$i}}</b>", $rpoint, $rlength ), PHP_EOL;
            echo "t-> Section Data2  = ", substr_replace ( substr ( $data2, $start, $length ), "<b style="color:red">{$data2 {$i}}</b>", $rpoint, $rlength ), PHP_EOL;
        }

    }

}

A better way to save to Database

$toDatabse = base64_encode(serialize($data));  // Save to database
$fromDatabase = unserialize(base64_decode($data)); //Getting Save Format 

<?php
$s = [
    [
        'title' => 'Услуги',
        'content' => 'На базе стоматологии «ПрезиДент» на Выставочной проводятся экспертные консультации, лечение под наркозом и с седацией, лечение под микроскопом; компьютерная томография и рентгенография, составляется план лечения. Имеется детское отделение.Оказываются услуги по таким направлениям, как терапия, хирургия, ортопедия, профессиональная гигиена, пародонтология. Предоставляются следующие виды услуг лечение кариеса и патологий пародонта, пломбирование зубов композитами, отбеливание эмали по технологии ZOOM 4, вживление имплантов и инсталляция коронок из металлокерамики и диоксид циркония.'
    ], [
        'title' => 'Проезд',
        'content' => 'До стоматологии «ПрезиДент» на Выставочной можно доехать на метро. Ближайшие остановки «Шелепиха» или "Выставочная". От "Выставочной" необходимо подняться к Экспоцентру повернуть налево и следовать прямо до стоматологии. От метро "Шелепиха" - поднявшись на поверхность, нужно сесть на любой автобус № т54, т66, 4, 69, 152 и проследовать до остановки «Детская больница». Покинув транспорт, надо повернуть на улицу Антонова-Овсеенко и пройти к высотному зданию по адресу ул. 3-я Красногвардейская дом 3 (вход с улицы Антонова-Овсеенко).' 
    ], [
        'title' => 'Парковка',
        'content' => 'Для пациентов есть бесплатная парковка. Въезд с улицы Антонова-Овсеенко. Для въезда на территорию нужно позвонить администратору за 2 минуты до прибытия.'
    ]
];
$s = serialize($s);
print $s;

Получаем

a:3:{i:0;a:2:{s:5:"title";s:12:"Услуги";s:7:"content";s:1085:"На базе стоматологии «ПрезиДент» на Выставочной проводятся экспертные консультации, лечение под наркозом и с седацией, лечение под микроскопом; компьютерная томография и рентгенография, составляется план лечения. Имеется детское отделение.Оказываются услуги по таким направлениям, как терапия, хирургия, ортопедия, профессиональная гигиена, пародонтология. Предоставляются следующие виды услуг лечение кариеса и патологий пародонта, пломбирование зубов композитами, отбеливание эмали по технологии ZOOM 4, вживление имплантов и инсталляция коронок из металлокерамики и диоксид циркония.";}i:1;a:2:{s:5:"title";s:12:"Проезд";s:7:"content";s:960:"До стоматологии «ПрезиДент» на Выставочной можно доехать на метро. Ближайшие остановки «Шелепиха» или "Выставочная". От "Выставочной" необходимо подняться к Экспоцентру повернуть налево и следовать прямо до стоматологии. От метро "Шелепиха" - поднявшись на поверхность, нужно сесть на любой автобус № т54, т66, 4, 69, 152 и проследовать до остановки «Детская больница». Покинув транспорт, надо повернуть на улицу Антонова-Овсеенко и пройти к высотному зданию по адресу ул. 3-я Красногвардейская дом 3 (вход с улицы Антонова-Овсеенко).";}i:2;a:2:{s:5:"title";s:16:"Парковка";s:7:"content";s:281:"Для пациентов есть бесплатная парковка. Въезд с улицы Антонова-Овсеенко. Для въезда на территорию нужно позвонить администратору за 2 минуты до прибытия.";}}

Если сравнить с вашей строкой, то разница только в заявленных длинах строк 1085 байт вместо 1094 и 960 вместо 966. Непонятно, куда и какие делись символы из оригинального текста, сравнивайте побайтно оригинальную строку и строку с ошибкой unserialize.
А в целом, IMHO, для хранения в базе данных лучше использовать JSON в кодировке utf8mb4, а если с этими данными надо ещё и активно работать, то выносить их в отдельную таблицу свойств.

    msm.ru

    Нравится ресурс?

    Помоги проекту!

    >
    Ошибка Error at offset 65531 of 65535 bytes

    • Подписаться на тему
    • Сообщить другу
    • Скачать/распечатать тему



    Сообщ.
    #1

    ,
    15.12.09, 22:13

      function.unserialize: Error at offset 65531 of 65535 bytes
      что это за ошибка и как выяснить какие данные ее вызывают?

      у меня проблемная строчка в функции которая вызывается из разных мест много раз


      Pr0[)!9Y



      Сообщ.
      #2

      ,
      15.12.09, 22:19

        Цитата orb @ 15.12.09, 22:13

        у меня проблемная строчка в функции которая вызывается из разных мест много раз

        Ну есть отладчики, да и в лоб: эхать перед каждым вызовом данные. Эхо перед ошибкой и будет данными ведь. В чем сложность?


        KirSSS



        Сообщ.
        #3

        ,
        16.12.09, 05:01

          Full Member

          ***

          Рейтинг (т): 9

          unserialize десериализирует объект из строки, в самой строке ошибка, на 65531 байте.
          эхом тут мало чего прояснишь, можно лишь увидеть что конкретно «не те данные» функции скармливаете.

          добавлю:
          вот пример сериализованного массива array(a, b, c, d, e)

          ExpandedWrap disabled

            a:5:{i:0;s:1:»a»;i:1;s:1:»b»;i:2;s:1:»c»;i:3;s:1:»d»;i:4;s:1:»e»;}

          если строка битая, например таккая

          ExpandedWrap disabled

            a:5:{i:0;s:1:»a»;i:1;s:1:»b»;i:2;s1:»c»;i:3;s:1:»d»;i:4;s:1:»e»;}

          (убрал одно двоеточие перед элементом с)
          то это вызовет ошибку

          ExpandedWrap disabled

            Notice: unserialize() [function.unserialize]: Error at offset 33 of 65 bytes in

          Сообщение отредактировано: KirSSS — 16.12.09, 05:08


          orb



          Сообщ.
          #4

          ,
          16.12.09, 06:49

            Цитата Pr0[)!9Y @ 15.12.09, 22:19

            Эхо перед ошибкой и будет данными ведь

            ошибка на 65531 символе :whistle:

            Monster

            fatalist



            Сообщ.
            #5

            ,
            16.12.09, 06:54

              Цитата orb @ 16.12.09, 06:49

              ошибка на 65531 символе

              Я в PHP так еще не делал, но полагаю, что можно try … catch и вывести подстроку +-5 символов от 65531-го… :rolleyes:


              orb



              Сообщ.
              #6

              ,
              16.12.09, 06:55

                Цитата fatalist @ 16.12.09, 06:54

                try … catch и

                не ловит

                Master

                negram



                Сообщ.
                #7

                ,
                16.12.09, 07:15

                  ExpandedWrap disabled

                    class ENotice extends Exception

                    {

                    }

                    function te($code, $message, $file, $line)

                    {

                    if ($code == E_NOTICE) {

                      throw new ENotice($message, $code);

                    }

                    }

                    set_error_handler(‘te’, E_NOTICE);

                    try {

                     unserialize(…);

                    } catch (ENotice $e) {

                     var_dump($e->getTrace());

                    }

                  а так ловит?


                  Pr0[)!9Y



                  Сообщ.
                  #8

                  ,
                  16.12.09, 09:20

                    Цитата orb @ 15.12.09, 22:13

                    of 65535

                    Уж не закончилась ли строка раньше времени, если она из базы например? Слишком уж число круглое =)


                    orb



                    Сообщ.
                    #9

                    ,
                    16.12.09, 18:21

                      ExpandedWrap disabled

                        s:3:»url»;s:30:»http://svet/shop/4/1/5/page_1/»;}i:709;a:2:{s:4:»name»;s:31

                        )

                      вот так заканчивается массив сбойный

                      Добавлено 16.12.09, 18:22

                      ExpandedWrap disabled

                        static $i = 0;

                        if ($i == 2) {

                              print_r($data);

                              die;

                            }

                        $data = unserialize($data[0]);

                      вот таким скриптом отладки выловил сбойные данные

                      Добавлено 16.12.09, 18:31
                      теперь другая проблема — как пофиксить ошибку :(


                      Pr0[)!9Y



                      Сообщ.
                      #10

                      ,
                      16.12.09, 18:54

                        Цитата Pr0[)!9Y @ 16.12.09, 09:20

                        Уж не закончилась ли строка раньше времени, если она из базы например?

                        Добавлено 16.12.09, 18:54
                        1) Данные откуда?
                        2) Исходные данные сериализуй и посмотри, может быть это на этапе сериализации проявляется.


                        orb



                        Сообщ.
                        #11

                        ,
                        16.12.09, 19:09

                          1. электронный магазин. самопал. Кто творец я не знаю
                          данные я знаю что такое

                          ExpandedWrap disabled

                            a:2:{s:4:»name»;s:21:»Modern 317″;s:3:»url»;s:25:»http://site/shop//page_1/»;}}i:14;

                          это один элемент товара, его линка для меню

                          Добавлено 16.12.09, 19:10
                          когда начала проявлять ошибка я не знаю
                          жду хозяина магазина и листаю логи


                          Pr0[)!9Y



                          Сообщ.
                          #12

                          ,
                          16.12.09, 19:31

                            orb,ну откуда данные то сериализованные беруться? Из сессии наврядли, из файла? из базы?
                            Так вот к чему клоню, если из базы, то посмотри что в этой таблице? Данные целы? Например может быть там тип поля TEXT, разработчик подумал что ему хватит навсегда, а туда помещается только 65535 символов.

                            Добавлено 16.12.09, 19:32
                            Тогда менять тип поля и заносить битые данные заново.


                            orb



                            Сообщ.
                            #13

                            ,
                            16.12.09, 19:45

                              из базы данных
                              но проблема в том что неизвестно когда произошла ошибка
                              и сколько данных находится в таком побитом виде


                              Pr0[)!9Y



                              Сообщ.
                              #14

                              ,
                              16.12.09, 19:51

                                Мне кажется проблему надо по шагам решать, сначала убедись что проблема в базе. Реши задачу программистскую. А пользовательскую будешь решать когда все будет работать.

                                Цитата orb @ 16.12.09, 19:45

                                но проблема в том что неизвестно когда произошла ошибка

                                Если мое предположние верно, тогда началось ровно тогда когда появился объект с длинными данными.


                                orb



                                Сообщ.
                                #15

                                ,
                                16.12.09, 19:56

                                  Цитата orb @ 16.12.09, 18:21

                                  ExpandedWrap disabled

                                    s:3:»url»;s:30:»http://svet/shop/4/1/5/page_1/»;}i:709;a:2:{s:4:»name»;s:31

                                    )

                                  вот так заканчивается массив сбойный

                                  тут видно что массив недозаписан

                                  0 пользователей читают эту тему (0 гостей и 0 скрытых пользователей)

                                  0 пользователей:

                                  • Предыдущая тема
                                  • PHP
                                  • Следующая тема

                                  Рейтинг@Mail.ru

                                  [ Script execution time: 0,0439 ]   [ 15 queries used ]   [ Generated: 10.02.23, 04:59 GMT ]  

                                  (PHP 4, PHP 5, PHP 7)

                                  unserialize
                                  Creates a PHP value from a stored representation

                                  Description

                                  mixed unserialize
                                  ( string $str
                                  [, array $options
                                  ] )

                                  unserialize() takes a single serialized variable and
                                  converts it back into a PHP value.

                                  Parameters

                                  str

                                  The serialized string.

                                  If the variable being unserialized is an object, after successfully
                                  reconstructing the object PHP will automatically attempt to call the
                                  __wakeup() member
                                  function (if it exists).

                                  Note:
                                  unserialize_callback_func directive

                                  It’s possible to set a callback-function which will be called,
                                  if an undefined class should be instantiated during unserializing.
                                  (to prevent getting an incomplete object «__PHP_Incomplete_Class».)
                                  Use your php.ini, ini_set() or .htaccess
                                  to define ‘unserialize_callback_func‘. Everytime an undefined class
                                  should be instantiated, it’ll be called. To disable this feature just
                                  empty this setting.

                                  options

                                  Any options to be provided to unserialize(), as an
                                  associative array.

                                  Valid options

                                  Name Type Description
                                  allowed_classes mixed
                                  Either an array of class names which should be
                                  accepted, FALSE to accept no classes, or TRUE to accept all
                                  classes. If this option is defined and
                                  unserialize() encounters an object of a class
                                  that isn’t to be accepted, then the object will be instantiated as
                                  __PHP_Incomplete_Class instead.


                                  Omitting this option is the same as defining it as TRUE: PHP
                                  will attempt to instantiate objects of any class.

                                  Return Values

                                  The converted value is returned, and can be a boolean,
                                  integer, float, string,
                                  array or object.

                                  In case the passed string is not unserializeable, FALSE is returned and
                                  E_NOTICE is issued.

                                  Changelog

                                  Version Description
                                  7.0.0 The options parameter has been added.
                                  5.6.0 Manipulating the serialised data by replacing C:
                                  with O: to force object instantiation without
                                  calling the constructor will now fail.

                                  Examples

                                  Example #1 unserialize() example


                                  <?php
                                  // Here, we use unserialize() to load session data to the
                                  // $session_data array from the string selected from a database.
                                  // This example complements the one described with serialize().
                                  $conn odbc_connect("webdb""php""chicken");
                                  $stmt odbc_prepare($conn"SELECT data FROM sessions WHERE id = ?");
                                  $sqldata = array($_SERVER['PHP_AUTH_USER']);
                                  if (!
                                  odbc_execute($stmt$sqldata) || !odbc_fetch_into($stmt$tmp)) {
                                      
                                  // if the execute or fetch fails, initialize to empty array
                                      
                                  $session_data = array();
                                  } else {
                                      
                                  // we should now have the serialized data in $tmp[0].
                                      
                                  $session_data unserialize($tmp[0]);
                                      if (!
                                  is_array($session_data)) {
                                          
                                  // something went wrong, initialize to empty array
                                          
                                  $session_data = array();
                                      }
                                  }
                                  ?>

                                  Example #2 unserialize_callback_func example


                                  <?php
                                  $serialized_object
                                  ='O:1:"a":1:{s:5:"value";s:3:"100";}';// unserialize_callback_func directive available as of PHP 4.2.0
                                  ini_set('unserialize_callback_func''mycallback'); // set your callback_functionfunction mycallback($classname
                                  {
                                      
                                  // just include a file containing your classdefinition
                                      // you get $classname to figure out which classdefinition is required
                                  }
                                  ?>

                                  Notes

                                  Warning

                                  FALSE is returned both in the case of an error and if unserializing
                                  the serialized FALSE value. It is possible to catch this special case by
                                  comparing str with
                                  serialize(false) or by catching the issued
                                  E_NOTICE.

                                  Warning

                                  Do not pass untrusted user input to unserialize().
                                  Unserialization can result in code being loaded and executed due to object
                                  instantiation and autoloading, and a malicious user may be able to exploit
                                  this. Use a safe, standard data interchange format such as JSON (via
                                  json_decode() and json_encode()) if
                                  you need to pass serialized data to the user.

                                  See Also

                                  • serialize() — Generates a storable representation of a value
                                  • Autoloading Classes
                                  • unserialize_callback_func
                                  • __wakeup()

                                  User Contributed Notes

                                  chris AT cmbuckley DOT co DOT uk

                                  7 years ago


                                  As mentioned in the notes, unserialize returns false in the event of an error and for boolean false. Here is the first solution mentioned, without using error handling:

                                  <?php
                                  function isSerialized($str) {
                                      return (
                                  $str == serialize(false) || @unserialize($str) !== false);
                                  }
                                  var_dump(isSerialized('s:6:"foobar";')); // bool(true)
                                  var_dump(isSerialized('foobar'));        // bool(false)
                                  var_dump(isSerialized('b:0;'));          // bool(true)
                                  ?>


                                  ErnestV

                                  2 years ago


                                  Just a note - if the serialized string contains a reference to a class that cannot be instantiated (e.g. being abstract) PHP will immediately die with a fatal error. If the unserialize() statement is preceded with a '@' to avoid cluttering the logs with warns or notices there will be absolutely no clue as to why the script stopped working. Cost me a couple of hours...

                                  arbie samong

                                  6 years ago


                                  __PHP_Incomplete_Class Object Demystified

                                  1. First take note of the output. A simple example:

                                  __PHP_Incomplete_Class Object (

                                  [__PHP_Incomplete_Class_Name] => SomeObject1

                                  [obj1property1] => somevalue1 [obj1property2] => __PHP_Incomplete_Class Object ( [__PHP_Incomplete_Class_Name] => SomeObject2 [obj2property1] => somevalue1 [obj2property2] => Array (

                                  ['key1'] => somevalue3, ['key2'] => somevalue4 ) ) )

                                  2. We analyze this and break it down.

                                  __PHP_Incomplete_Class Object tells you there is an object that needs to be declared somehow.

                                  __PHP_Incomplete_Class_Name simply tells you the expected class name. It is just one of the properties for now.

                                  So we have:

                                  a) an unknown object that has a class name SomeObject1 (first class)

                                  b) it has 2 properties, namely obj1property1 and obj2property2

                                  c) obj2property2 is itself an object whose class name is SomeObject2 (the second class)

                                  d) SomeObject2 has two properties, obj2property1 and obj2property2

                                  e) obj2property2 is an array that contains two elements

                                  3. Now that we have an idea of the structure, we shall create class definitions based from it. We will just create properties for now, methods are not required as a minimum.

                                  <?php

                                  class SomeObject1 {

                                          public
                                  $obj1property1;

                                          public
                                  $obj1property2;

                                  }

                                  class
                                  SomeObject2 {

                                          public
                                  $obj2property1;

                                          public
                                  $obj2property2;

                                  }

                                  ?>



                                  4. Have that accessible to your script and it will solve the __PHP_Incomplete_Class Object problem as far as the output is concerned. Now you will have:

                                  SomeObject1 ( [obj1property1] => somevalue1 [obj1property2] => SomeObject2 ( [obj2property1] => somevalue1 [obj2property2] => Array ( ['key1'] => somevalue3, ['key2'] => somevalue4 ) ) )

                                  As you will notice, __PHP_Incomplete_Class Object is gone and replaced by the class name. The property __PHP_Incomplete_Class_Name is also removed.

                                  5. As for the array property obj2property2, we can directly access that and just assume that it is an array and loop through it:

                                  <?php
                                  // this will be SomeObject1

                                  $data = unserialize($serialized_data);
                                  // this will be SomeObject2

                                  $data2 = $data->obj1property2();

                                  foreach(

                                  $data2->obj2property2 as $key => $value):

                                           print
                                  $key.' : '. $value .'<br>';

                                  endforeach;
                                  ?>



                                  Outputs:

                                  key1 : somevalue3

                                  key2 : somevalue4

                                  That's it. You can add more methods on the class declarations for the given properties, provided you keep your original output as basis for the data types.


                                  double at dumpit dot com

                                  9 years ago


                                  This little function will check whether the serialized string is well formed.

                                  PHP < 6 because i'd heard changes will be made in this php-intern function,
                                  maybe it could be edited easy for it.

                                  <?phpfunction wd_check_serialization( $string, &$errmsg )
                                  {
                                  $str = 's';
                                     
                                  $array = 'a';
                                     
                                  $integer = 'i';
                                     
                                  $any = '[^}]*?';
                                     
                                  $count = 'd+';
                                     
                                  $content = '"(?:\";|.)*?";';
                                     
                                  $open_tag = '{';
                                     
                                  $close_tag = '}';
                                     
                                  $parameter = "($str|$array|$integer|$any):($count)" . "(?:[:]($open_tag|$content)|[;])";           
                                     
                                  $preg = "/$parameter|($close_tag)/";
                                      if( !
                                  preg_match_all( $preg, $string, $matches ) )
                                      {           
                                         
                                  $errmsg = 'not a serialized string';
                                          return
                                  false;
                                      }   
                                     
                                  $open_arrays = 0;
                                      foreach(
                                  $matches[1] AS $key => $value )
                                      {
                                          if( !empty(
                                  $value ) && ( $value != $array xor $value != $str xor $value != $integer ) )
                                          {
                                             
                                  $errmsg = 'undefined datatype';
                                              return
                                  false;
                                          }
                                          if(
                                  $value == $array )
                                          {
                                             
                                  $open_arrays++;                               
                                              if(
                                  $matches[3][$key] != '{' )
                                              {
                                                 
                                  $errmsg = 'open tag expected';
                                                  return
                                  false;
                                              }
                                          }
                                          if(
                                  $value == '' )
                                          {
                                              if(
                                  $matches[4][$key] != '}' )
                                              {
                                                 
                                  $errmsg = 'close tag expected';
                                                  return
                                  false;
                                              }
                                             
                                  $open_arrays--;
                                          }
                                          if(
                                  $value == $str )
                                          {
                                             
                                  $aVar = ltrim( $matches[3][$key], '"' );
                                             
                                  $aVar = rtrim( $aVar, '";' );
                                              if(
                                  strlen( $aVar ) != $matches[2][$key] )
                                              {
                                                 
                                  $errmsg = 'stringlen for string not match';
                                                  return
                                  false;
                                              }
                                          }
                                          if(
                                  $value == $integer )
                                          {
                                              if( !empty(
                                  $matches[3][$key] ) )
                                              {
                                                 
                                  $errmsg = 'unexpected data';
                                                  return
                                  false;
                                              }
                                              if( !
                                  is_integer( (int)$matches[2][$key] ) )
                                              {
                                                 
                                  $errmsg = 'integer expected';
                                                  return
                                  false;
                                              }
                                          }
                                      }       
                                      if(
                                  $open_arrays != 0 )
                                      {
                                         
                                  $errmsg = 'wrong setted arrays';
                                          return
                                  false;
                                      }
                                      return
                                  true;
                                  }
                                  ?>


                                  Ray.Paseur often uses Gmail

                                  2 years ago


                                  In the Classes and Objects docs, there is this: In order to be able to unserialize() an object, the class of that object needs to be defined.

                                  Prior to PHP 5.3, this was not an issue.  But after PHP 5.3 an object made by SimpleXML_Load_String() cannot be serialized.  An attempt to do so will result in a run-time failure, throwing an exception.  If you store such an object in $_SESSION, you will get a post-execution error that says this:

                                  Fatal error: Uncaught exception 'Exception' with message 'Serialization of 'SimpleXMLElement' is not allowed' in [no active file]:0 Stack trace: #0 {main} thrown in [no active file] on line 0

                                  The entire contents of the session will be lost.  Hope this saves someone some time!

                                  <?php // RAY_temp_ser.php
                                  error_reporting(E_ALL);
                                  session_start();
                                  var_dump($_SESSION);
                                  $_SESSION['hello'] = 'World';
                                  var_dump($_SESSION);// AN XML STRING FOR TEST DATA
                                  $xml = '<?xml version="1.0"?>
                                  <families>
                                    <parent>
                                      <child index="1" value="Category 1">Child One</child>
                                    </parent>
                                  </families>'
                                  ;// MAKE AN OBJECT (GIVES SimpleXMLElement)
                                  $obj = SimpleXML_Load_String($xml);// STORE THE OBJECT IN THE SESSION
                                  $_SESSION['obj'] = $obj;


                                  daniel at fourstaples dot com

                                  6 years ago


                                  Here's a simple function to get the class of a serialized string (that is, the type of object that will be returned if it's unserialized):

                                  <?php
                                  function get_serial_class($serial) {
                                     
                                  $types = array('s' => 'string', 'a' => 'array', 'b' => 'bool', 'i' => 'int', 'd' => 'float', 'N;' => 'NULL');$parts = explode(':', $serial, 4);
                                      return isset(
                                  $types[$parts[0]]) ? $types[$parts[0]] : trim($parts[2], '"');
                                  }
                                  ?>

                                  I use this when saving a serialized object to a cookie, to make sure it is the right type when I go to unserialize it.

                                  The type names are the same format/case as you would see if you did a var_dump().


                                  chris at pollett dot org

                                  9 months ago


                                  When you serialize an object of a class from a particular namespace, the namespace is recorded as part of the serialization. If you decide to change this namespace's name, it can be hard to read in old serialized objects. I.e., suppose you had serialized an object of type fooA, you change the namespace of your project to goo but otherwise leave the class definition of A unchanged. You would like to be able to unserialize the object as gooA, instead unserialization will only create a partial object. To fix this in the case where you don't have nested objects in your class definition, you can use the following simple rename function:
                                  /**
                                  * Used to change the namespace of a serialized php object (assumes doesn't
                                  * have nested subobjects)
                                  *
                                  * @param string $class_name new fully qualified name with namespace
                                  * @param string $object_string serialized object
                                  *
                                  * @return string serialized object with new name
                                  */
                                  function renameSerializedObject($class_name, $object_string)
                                  {
                                      /*  number of digits in the length of name of the object needs to be
                                          less than 12 digits (probably more like 4) for this to work.
                                      */
                                      $name_length = intval(substr($object_string, 2, 14));
                                      $name_space_info_length = strlen("O:".$name_length.":") +
                                          $name_length + 2; // 2 for quotes;
                                      $object_string = 'O:' .
                                          strlen($class_name) . ':"'. $class_name.'"' .
                                          substr($object_string, $name_space_info_length);
                                      return $object_string;
                                  }

                                  suman dot jis at gmail dot com

                                  4 years ago


                                  I was getting unserialize()  Error at offset error.

                                  If you face similar problem  then use the following procedure

                                  $auctionDetails = preg_replace('!s:(d+):"(.*?)";!se', "'s:'.strlen('$2').':"$2";'", $dataArr[$i]['auction_details'] );
                                  $auctionDetails = unserialize($auctionDetails);


                                  chris at colourlovers dot com

                                  4 years ago


                                  Anyone having trouble serializing data with SimpleXMLElement objects stored within it, check this out:

                                  This will traverse $data looking for any children which are instances of SimpleXMLElement, and will run ->asXML() on them, turning them into a string and making them serializable. Other data will be left alone.

                                  <?php
                                  function exportNestedSimpleXML($data) {
                                      if (
                                  is_scalar($data) === false) {
                                          foreach (
                                  $data as $k => $v) {
                                              if (
                                  $v instanceof SimpleXMLElement) {
                                                 
                                  $v = str_replace(" ","r",$v->asXML());
                                              } else {
                                                 
                                  $v = exportNestedSimpleXML($v);
                                              }

                                              if (

                                  is_array($data)) {
                                                 
                                  $data[$k] = $v;
                                              } else if (
                                  is_object($data)) {
                                                 
                                  $data->$k = $v;
                                              }
                                          }
                                      }

                                      return

                                  $data;
                                  }
                                  $data = array (
                                     
                                  "baz" => array (
                                         
                                  "foo" => new stdClass(),
                                         
                                  "int" => 123,
                                         
                                  "str" => "asdf",
                                         
                                  "bar" => new SimpleXMLElement('<?xml version="1.0" encoding="UTF-8"?><foo>bar</foo>'),
                                      )
                                  );
                                  var_dump($data);
                                  /*array(1) {
                                    ["baz"]=>
                                    array(4) {
                                      ["foo"]=>
                                      object(stdClass)#3 (0) {
                                      }
                                      ["int"]=>
                                      int(123)
                                      ["str"]=>
                                      string(4) "asdf"
                                      ["bar"]=>
                                      object(SimpleXMLElement)#4 (1) {
                                        [0]=>
                                        string(3) "bar"
                                      }
                                    }
                                  }*/
                                  var_dump(exportNestedSimpleXML($data));
                                  /*array(1) {
                                    ["baz"]=>
                                    array(4) {
                                      ["foo"]=>
                                      object(stdClass)#3 (0) {
                                      }
                                      ["int"]=>
                                      int(123)
                                      ["str"]=>
                                      string(4) "asdf"
                                      ["bar"]=>
                                      string(54) "<?xml version="1.0" encoding="UTF-8"?>
                                  <foo>bar</foo>
                                  "
                                    }
                                  }
                                  */
                                  ?>


                                  Fagzal

                                  6 years ago


                                  To all who have problem with quoting and slashes when storing serialized data in MySQL: you are probably doing it wrong.

                                  Use e.g. PDO with placeholders and the blob column type, and it will Just Work.


                                  w dot laurencine at teknoa dot net

                                  7 years ago


                                  When dealing with a string which contain "r", it seems that the length is not evaluated correctly. The following solves the problem for me :

                                  <?php
                                  // remove the r caracters from the $unserialized string
                                  $unserialized = str_replace("r","",$unserialized);// and then unserialize()
                                  unserialize($unserialized);
                                  ?>


                                  Are Pedersen

                                  9 years ago


                                  Be aware that if useing serialize/unserialize in a serverfarm with both 32bit and 64bit servers you can get unexpected results.

                                  Ex: if you serialize an integer with value of 2147483648 on a 64bit system and then unserialize it on a 32bit system you will get the value -2147483648 instead. This is because an integer on 32bit cannot be above 2147483647 so it wraps.


                                  martin dot goldinger at netserver dot ch

                                  10 years ago


                                  When you use sessions, its very important to keep the sessiondata small, due to low performance with unserialize. Every class shoud extend from this class. The result will be, that no null Values are written to the sessiondata. It will increase performance.

                                  <?
                                  class BaseObject
                                  {
                                      function __sleep()
                                      {
                                          $vars = (array)$this;
                                          foreach ($vars as $key => $val)
                                          {
                                              if (is_null($val))
                                              {
                                                  unset($vars[$key]);
                                              }
                                          }   
                                          return array_keys($vars);
                                      }
                                  };
                                  ?>


                                  Chris Hayes (chris at hypersites dot com)

                                  11 years ago


                                  In reply to the earlier post about having to include object definitions *before* using unserialize.  There is a workaround for this.

                                  When an object is serialized, the first bit of the string is actually the name of the class.  When an unknown object is unserialized, this is maintained as a property.  So if you serialize it again, you get back the exact same string as if you'd serialized the original object.  Basically, to cut to the point...

                                  If you use

                                  $_SESSION['my_object'] = unserialize(serialize($_SESSION['my_object']))

                                  then you get back an object of the correct type, even if the session had originally loaded it as an object of type stdClass.


                                  smilesrg at gmail dot com

                                  8 months ago


                                  I faced with error when serializing/deserializing an object. The error looks like
                                  Notice: unserialize(): Error at offset 2 of 52 bytes in file.php on line 130

                                  and found solution here: http://davidwalsh.name/php-serialize-unserialize-issues

                                  The safe way to serialize and unserialize:

                                  //to safely serialize
                                  $serialized = base64_encode(serialize($var));

                                  //to unserialize...
                                  $unserialized = unserialize(base64_decode($var));


                                  walf

                                  4 years ago


                                  a replacement for unserialize that returns whether it worked and populates the unserialized variable by reference:
                                  <?php
                                  function funserialize($serialized, &$into) {
                                      static
                                  $sfalse;
                                      if (
                                  $sfalse === null)
                                         
                                  $sfalse = serialize(false);
                                     
                                  $into = @unserialize($serialized);
                                      return
                                  $into !== false || rtrim($serialized) === $sfalse;//whitespace at end of serialized var is ignored by PHP
                                  }$s_foo = 'b:0;';
                                  var_dump(funserialize($s_foo, $foo), $foo);$s_bar = 'bar';
                                  var_dump(funserialize($s_bar, $bar), $bar);$s_foo = 'a:0:{};';
                                  var_dump(funserialize($s_foo, $foo), $foo);?>
                                  gives:

                                  bool(true)
                                  bool(false)

                                  bool(false)
                                  bool(false)

                                  bool(true)
                                  array(0) {
                                  }


                                  aderyn at nowhere dot tld

                                  12 years ago


                                  A quick note:
                                  If you store a serialized object in a session, you have to include the class _before_ you initialize (session_start()) the session.

                                  MBa

                                  4 years ago


                                  To check if a string is serialized:

                                  $blSerialized=(@unserialize($sText)||$sText=='b:0;');


                                  BenBE at omorphia dot de

                                  9 years ago


                                  When trying to serialize or unserialize recursive arrays or otherwise linked data you might find the undocumented R data type quite useful.

                                  If you want a array like the one produced with
                                  <?
                                  $a = array();
                                  $a[0] =& $a;
                                  ?>
                                  serialized you can store it using a string simular to this one:
                                  <?
                                  $a = unserialize("a:1:{i:0;R:1;}");
                                  ?>

                                  Both sources will make $a hold an array that self-references itself in index 0.

                                  The argument for R is the index of the created sub-variable of the serialize-string beginning with 1.


                                  chad 0x40 herballure 0x2e com

                                  9 years ago


                                  When unserializing in PHP5 (behavior observed with 5.1.2), __autoload() will be checked first, and unserialize_callback_func called only if __autoload failed to load the class definition.

                                  Ates Goral

                                  8 years ago


                                  If instead of using JSON, you'd like to stick with PHP-style serialization, here's some JavaScript code I posted at http://magnetiq.com for serializing JavaScript objects in PHP fashion:

                                  /* Returns the class name of the argument or undefined if
                                     it's not a valid JavaScript object.
                                  */
                                  function getObjectClass(obj)
                                  {
                                      if (obj && obj.constructor && obj.constructor.toString)
                                      {
                                          var arr = obj.constructor.toString().match(
                                              /functions*(w+)/);

                                          if (arr && arr.length == 2)
                                          {
                                              return arr[1];
                                          }
                                      }

                                      return undefined;
                                  }

                                  /* Serializes the given argument, PHP-style.

                                     The type mapping is as follows:

                                     JavaScript Type    PHP Type
                                     ---------------    --------
                                     Number             Integer or Decimal
                                     String             String
                                     Boolean            Boolean
                                     Array              Array
                                     Object             Object
                                     undefined          Null

                                     The special JavaScript object null also becomes PHP Null.
                                     This function may not handle associative arrays or array
                                     objects with additional properties well.
                                  */
                                  function phpSerialize(val)
                                  {
                                      switch (typeof(val))
                                      {
                                      case "number":
                                          return (Math.floor(val) == val ? "i" : "d") + ":" +
                                              val + ";";
                                      case "string":
                                          return "s:" + val.length + ":"" + val + "";";
                                      case "boolean":
                                          return "b:" + (val ? "1" : "0") + ";";
                                      case "object":
                                          if (val == null)
                                          {
                                              return "N;";
                                          }
                                          else if ("length" in val)
                                          {
                                              var idxobj = { idx: -1 };

                                              return "a:" + val.length + ":{" + val.map(
                                                  function (item)
                                                  {
                                                      this.idx++;

                                                      var ser = phpSerialize(item);

                                                      return ser ?
                                                          phpSerialize(this.idx) + ser :
                                                          false;
                                                  }, idxobj).filter(
                                                  function (item)
                                                  {
                                                      return item;
                                                  }).join("") + "}";
                                          }
                                          else
                                          {
                                              var class_name = getObjectClass(val);

                                              if (class_name == undefined)
                                              {
                                                  return false;
                                              }

                                              var props = new Array();

                                              for (var prop in val)
                                              {
                                                  var ser = phpSerialize(val[prop]);

                                                  if (ser)
                                                  {
                                                      props.push(phpSerialize(prop) + ser);
                                                  }
                                              }
                                              return "O:" + class_name.length + ":"" +
                                                  class_name + "":" + props.length + ":{" +
                                                  props.join("") + "}";
                                          }
                                      case "undefined":
                                          return "N;";
                                      }

                                      return false;
                                  }

                                  On the client side, you can pass in a complex (nested) JavaScript object to the phpSerialize function to get a PHP-style serialized representation. This string can be posted back and directly passed to the unserialize function to yield a representation of the complex object in PHP realm. Use of this technique requires caution on security matters.


                                  Понравилась статья? Поделить с друзьями:
                                • Unrecognized database format filename error 3343
                                • Unrouteable address ошибка почты
                                • Unreal tournament 2004 как изменить разрешение экрана
                                • Unrouteable address как исправить
                                • Unreal engine text render error 2715 перевод