Джанго выполняет шаги или обрабатывает сообщения через REST - PullRequest
0 голосов
/ 01 ноября 2019

В целях обучения я хочу реализовать следующую вещь:

У меня есть скрипт, который запускает селен, например, в фоновом режиме, и у меня есть несколько сообщений журнала, которые помогают мне увидеть, что происходит в терминале,Но я хочу получить те же сообщения в моем REST-запросе к приложению Angular.

print('Started')
print('Logged in')
...
print('Processing')
...
print('Success')

В моем файле view.py

class RunTask(viewsets.ViewSet):
queryset = Task.objects.all()

@action(detail=False, methods=['GET'], name='Run Test Script')
def run(self, request, *args, **kwargs):
    task = task()

    if valid['success']:
        return Response(data=task)
    else:
        return Response(data=task['message'])

 def task()
    print('Staring')
    print('Logged in')
    ...
    print('Processing')
    ...
    print('Success')

    return {
        'success': True/False,
        'message': 'my status message'
    }

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

Или как я могу угадать о состоянии своего процесса?

1 Ответ

0 голосов
/ 01 ноября 2019

К сожалению, это не , что просто. Действительно, API REST позволяет запустить задачу, но, поскольку он выполняется в том же потоке, HTTP-запрос будет блокироваться до завершения задачи перед отправкой ответа. Ваши операторы print будут появляться не в ответе HTTP, а на выходных данных вашего сервера (если вы посмотрите на оболочку, в которой вы запустили python manage.py runserver, вы увидите эти print операторы).

ТеперьЕсли вы хотите получать эти данные в режиме реального времени, вам придется искать WebSockets. Они позволяют вам открыть «туннель» между браузером и сервером и отправлять / получать сообщения в режиме реального времени. Библиотека django-channel позволяет вам их реализовать.


Однако для длительных фоновых задач (например, Selenium scraper) я бы посоветовал заглянуть в Очередь задач сельдерея . По сути, ваш процесс Django будет планировать задачу в очередь. Задачи в очереди будут выполняться одним (или несколькими!) «Рабочими» процессами. Преимущество этого состоит в том, что ваш процесс Django не будет заблокирован длинной задачей: он просто добавляет некоторую работу в очередь и затем отвечает.

Когда вы добавляете задачи в очередь, Celery даст вамуникальный идентификатор для этой задачи, который вы можете вернуть в ответе HTTP. Затем вы можете очень хорошо реализовать другую конечную точку, которая принимает идентификатор задачи в параметре и возвращает состояние задачи (ожидает ли она? Выполнено? Не выполнено?).

Чтобы это работало, вам придется настроить«брокер», вид базы данных, в которой будут храниться задачи и их результаты (обычно RabbitMQ или Redis). В документации по сельдерею это хорошо объясняется: https://docs.celeryproject.org/en/latest/getting-started/brokers/index.html

В любом случае, это не тривиальная вещь, и для достижения каких-то результатов потребуется довольно много работы;но интересно посмотреть, как он расширяет возможности классического HTTP-сервера.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...