just-work / django-celery-rpc

Remote access from one system to models of another one using Celery machinery.

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

`pipe` support

ttyS15 opened this issue · comments

There are needs to run several task as one batch (may be as atomic action).

Requested by @bourivouh

@bourivouh, есть идея как это сделать и вроде без сложных заморочек.

# Клиент
from celery_rpc.client import Client()
c = Client()

# Создаётся прокси-билдер, который внутри держит ссылку на c  
p = c.pipe(atomic=True)

# Компанует во внутренней структуре данных о цепочке задач. Аналогично  Model.objects.filter().order_by()[:]. 
# Для конструирования комманд есть метод Client.prepare_task()
p = p.filter(...).update(...)
p = p.delete(...)

# Выполняет отправку через клиент с.request(c.PIPE_TASK, data), где дата - данные о задачах
r = p.send()

# Тем временем на сервере
@task(bind=True)
def pipe(data, atomic=False):

   context_manager = atomic_commit_on_success if atomic else FakeAtomic
   result = []

   with context_manager:
      for task, args, kwargs in data:
        t = self.app.tasks[task]
        r.append(t.apply(*args, **kwargs)

   return result

Нет желания запилить? ;)

Возможен ли такой кейс?

  • Создать объект A,
  • Создать объект Б другой модели с FK на объект 1,
  • Выполнить call c ID объекта 2?

И все в рамках одной транзакции.

По логике такой кейс будет очень тяжелый если первым идет например p.filter() с 100500 записями. Хотя... в рамках одного процесса это будет ссылка на уже имеющийся объект.

И как узнать у второй задачи что куда подставлять от первой, если только:

p.filter('modelA', status=active).create('modelB', title='haha', st_fk='{values[0].pk}').call('func', obj_id='{values.pk}')

Хотелось бы сюда добавить что-то такое:

#34 (comment)