2016-11-27 33 views
7

Mam złożoną strukturę, która jest zapisana w bazie danych MySQL przy użyciu funkcji sericalize(), a następnie przekonwertowana z powrotem przy użyciu metody unserialize(). Po migracji systemu z PHP 5.3 do PHP 5.6 i odserializowaniu w 5.6 danych, które były serializowane na 5.3, struktury są uszkodzone. Niektóre odniesienia do obiektów są teraz wyświetlane jako tablice.Migracja serializacji PHP z PHP 5.3 do PHP 5.6

Moje pytania są następujące:

  1. Czy istnieje specyfikacja o różnej kodowania używanego przez serializacji/odserializacji w różnych wersjach PHP? (Nie mogłem znaleźć niczego konkretnego w moich wyszukiwaniach w Google lub w dokumentacji na PHP.net)

  2. Jak mogę przekonwertować dane serializowane z kodu PHP 5.3 na kodowanie PHP 5.6?

+0

Witam, Czy możesz podać więcej informacji o serializowaniu? Czy jest to klasa, czy tylko zbiór danych? –

+1

Po deserializacji obiektów należy uwzględnić definicje klas w kodzie. Jeśli więc testujesz poza zwykłą podstawą kodu z miejsca, w którym zapisałeś obiekty, lub jeśli zmieniłeś strukturę obiektu, nie będą one poprawnie deserializowane. Jeśli chcesz zmienić strukturę obiektu, zachowaj stare obiekty, a następnie odtwórz nowe obiekty, korzystając z nowej struktury i ponownie zsynchronizuj. (Nie publikuję jako odpowiedzi, ponieważ nie jestem w stanie jej przetestować - ale są to rzeczy, których należy szukać!). – Robbie

Odpowiedz

1

Można konwertować odcinkach danych do JSON (przy użyciu instalacji PHP 5.3), z zastrzeżeniem, że do bazy danych, a następnie wykonaj opposit (przy użyciu instalacji PHP 5.6).

Od 5,3 do JSON:

$data = unserialize($strSerializedData); 
$jsonData = json_encode($data); 

Od JSON do 5,6:

$data = json_decode($jsonData); 
$strSerializedData= serialize($data); 

Być może trzeba dostosować opcje wysyłania do json_decode pasujące do oryginalnych danych.

Ta opcja zależy od tego, jakie dane są serializowane. Jeśli twoje dane to klasy, to nie zadziała.

Ponadto, problem może być związany z niniejszej noty w dokumentacji (here):

5.6.0 Manipulowanie danych odcinkach zastępując C: z O: zmusić wystąpienia obiektu bez wywoływania konstruktora będzie teraz nie.

+0

Jako że pytanie dotyczy serializacji/deserializacji obiektów, i poprawnie wskazujesz "Jeśli twoje dane to klasy, to by nie działało. " wtedy tak - to nie zadziała. Możesz utworzyć metodę "toJSON()" i "fromJSON()" w klasie i użyć jej do uzyskania dostępu do elementów wewnętrznych, ale jeśli zajdziesz tak daleko, możesz równie dobrze napisać własne funkcje serliaze/deserialize! Aby to zrobić, użyj interfejsu 'serializowalnego' (http://php.net/manual/en/class.serializable.php). – Robbie

+0

Uzgodniono, że to nie zadziała w przypadku klasy. Pytanie wymagałoby wyjaśnienia. –

+0

Jest to rzeczywiście obiekt z klasy, którą serializuję. Obiekt ma odniesienia do obiektów tej samej klasy, a także do innych klas. Niektóre z tych klas z kolei odnoszą się do obiektu, do którego się odnoszą. Używając serialize(), te odnośniki są oznaczone przez r:, po którym następuje liczba. Niektóre z tych odniesień są uszkodzone, gdy zostaną odpakowane w PHP 5.6, a zamiast tego powinien to być obiekt klasy w tablicy. –

2

Tak, serializacja obiektów została zmieniona w PHP5.6. W szczególności wiele obszarów związanych z serializacji obiektów były uporządkowywane w PHP5.6

Jest niejasne uwaga wspomnieć o tym w PHP unserialize manual:

5.6.0 Manipulowanie danych odcinkach zastępując C: z O: Aby wymusić instancję obiektu bez wywoływania konstruktora, nie będzie się teraz dziać .

Jednak spojrzenie na listę błędów ujawniło, że pod maską pojawiło się trochę więcej niż w report 68099.Stwierdza również, że oryginalny format ma oficjalnej dokumentacji:

„oryginalne zachowanie (które pozwalają stary format serialize być wykorzystywane do zajęć z wykorzystaniem nowego formatu) nigdy nie została udokumentowana ani oficjalnie wspierany”

Należy pamiętać, że końcowy wynik tej dyskusji było "Will not fix".

Więc w zasadzie, dostępne opcje to:

  • Spróbuj jeden z pozostałych serializers jako sposób eksportowania danych pomiędzy wersjami PHP. Takich jak session_encode, które mogą również obsługiwać obiekty.

  • Skrypt konwersji. Istnieje obszernie udokumentowana wersja aktualnego formatu na PHP internals, której można użyć z iteratorem w starym formacie, aby zaktualizować składnię.