2013-08-15 2 views
3

заранее спасибо :)Джанго и сельдерей: не удался рассол задача

У меня есть этот асинхронный сельдерей задача вызов:

update_solr.delay(id, context) 

где идентификатор представляет собой целое число и контекст является Python ДИКТ.

Мое определение задачи выглядит следующим образом:

@task 
def update_solr(id, context): 
    clip = Clip.objects.get(pk=id) 
    clip_serializer = SOLRClipSerializer(clip, context=context) 
    response = requests.post(url, data=clip_serializer.data) 

где clip_serializer.data является ДИКТ и url является строка, представляющая URL.

Когда я пытаюсь вызвать update_solr.delay(), я получаю эту ошибку:

PicklingError: Can't pickle <type 'instancemethod'>: attribute lookup __builtin__.instancemethod failed 

Ни один из аргументов к задаче методы экземпляра, так что я запутался.

Когда код задачи запускается синхронно, нет ошибки.

Обновление: исправлено за комментарий о передаче pk вместо объекта.

+1

Чтобы избежать условий гонки и уменьшить размер полезной нагрузки, лучше передать модель ПК, а не экземпляр модели. – AndrewS

+0

Совершенно верно, но это не решает проблему. – hamsterdam

+0

Что-то * внутри объектов - это метод экземпляра (то есть вы помещаете Object.foomethod в словарь или что-то подобное), в месте, где маринование не может его рассолить. –

ответ

3

context ДИКТ имел объект в нем, без ведома мне ...

Чтобы исправить, я выполнил код, зависящий от context перед вызовом асинхронного и просто прошел Dict с только нативными типами:

def post_save(self, obj, created=False): 
    context = self.get_serializer_context() 
    clip_serializer = SolrClipSerializer(obj, context=context) 
    update_solr.delay(clip_serializer.data) 

задача закончилась так:

@task 
def update_solr(data): 
    response = requests.post(url, data=data) 

Это работает прекрасно, потому что единственная цель делая это асинхронной задача состоит в т ake POST не блокирует.

Спасибо за помощь!

0
import pickle 
class X: 
    def y(self): 
     pass 

pickle.dumps(X.y) 

Рассол работает рекурсивно, так что может быть в любом месте вашего графа объектов. Вам было дано решение - перенести только минимальные объекты, то есть первичные ключи и т. Д. Вместо объектов модели Django.

+1

Я сделал и все еще получаю ту же ошибку. Я обновлю. – hamsterdam

1

Попробуйте передать первичный ключ экземпляра модели (pk). Это намного проще рассолить, уменьшить полезную нагрузку и избежать условий гонки.

+0

Готово. Такая же ошибка. – hamsterdam

+0

Извините - вы сказали, что это исправлено ;-) Вы использовали метод без сельдерея? – AndrewS

+0

Я заработал, посмотрю на мой ответ. – hamsterdam

Смежные вопросы