Десериализация cPickle в Python из PHP? - PullRequest
6 голосов
/ 15 июня 2010

Мне нужно десериализовать словарь в PHP, который был сериализован с использованием cPickle в Python .

В этом конкретном случае я, вероятно, мог бы просто повторно получить требуемую информацию , но есть ли лучший способ? Какие-нибудь расширения для PHP, которые позволили бы мне десериализовать более естественным образом весь словарь?

Очевидно, он сериализован в Python так:

import cPickle as pickle

data = { 'user_id' : 5 }
pickled = pickle.dumps(data)
print pickled

Содержимое такой сериализации не может быть легко вставлено сюда, потому что оно содержит двоичные данные.


Решение

Так как конец Python - Django, я закончил тем, что создал собственный JSON SessionStore.

Ответы [ 4 ]

7 голосов
/ 15 июня 2010

Если вы хотите обмениваться объектами данных между программами, написанными на разных языках, может быть проще сериализовать / десериализовать, используя вместо этого что-то вроде JSON .Большинство основных языков программирования имеют библиотеку JSON.

5 голосов
/ 15 июня 2010

Можете ли вы сделать системный вызов? Вы можете использовать такой скрипт на python для преобразования данных pickle в json:

# pickle2json.py
import sys, optparse, cPickle, os
try:
    import json
except:
    import simplejson as json

# Setup the arguments this script can accept from the command line
parser = optparse.OptionParser()
parser.add_option('-p','--pickled_data_path',dest="pickled_data_path",type="string",help="Path to the file containing pickled data.")
parser.add_option('-j','--json_data_path',dest="json_data_path",type="string",help="Path to where the json data should be saved.")
opts,args=parser.parse_args()

# Load in the pickled data from either a file or the standard input stream
if opts.pickled_data_path:
    unpickled_data = cPickle.loads(open(opts.pickled_data_path).read())
else:
    unpickled_data = cPickle.loads(sys.stdin.read())

# Output the json version of the data either to another file or to the standard output
if opts.json_data_path:
    open(opts.json_data_path, 'w').write(json.dumps(unpickled_data))
else:
    print json.dumps(unpickled_data)

Таким образом, если вы получаете данные из файла, вы можете сделать что-то вроде этого:

<?php
    exec("python pickle2json.py -p pickled_data.txt", $json_data = array());
?>

или, если вы хотите сохранить его в файл, это:

<?php
    system("python pickle2json.py -p pickled_data.txt -j p_to_j.json");
?>

Весь приведенный выше код, вероятно, не идеален (я не PHP-разработчик), но подойдет ли вам что-нибудь подобное?

1 голос
/ 15 июня 2010

Если рассол создается с помощью кода, который вы показали, тогда он не будет содержать двоичные данные - если вы не называете новые строки "двоичными данными".Смотрите Документы Python .Следующий код был запущен Python 2.6.

>>> import cPickle
>>> data = {'user_id': 5}
>>> for protocol in (0, 1, 2): # protocol 0 is the default
...     print protocol, repr(cPickle.dumps(data, protocol))
...
0 "(dp1\nS'user_id'\np2\nI5\ns."
1 '}q\x01U\x07user_idq\x02K\x05s.'
2 '\x80\x02}q\x01U\x07user_idq\x02K\x05s.'
>>>

Что из вышеперечисленного больше всего похоже на то, что вы видите?Можете ли вы опубликовать содержимое маринованного файла в том виде, в котором оно отображается шестнадцатеричным редактором / дампером, или каким-либо другим эквивалентом Python repr ()?Сколько предметов в типичном словаре?Какие типы данных, кроме "целое число" и "строка 8-битных байтов" (какая кодировка?)?

0 голосов
/ 20 февраля 2014

У меня была такая же проблема. Я не нашел решения, поэтому я создал свой собственный минималистичный порт модуля python в php. Позже я нашел Zend Serializer Adapter PythonPickle от Zend Framework.

...