Как сделать три функции одной кнопкой отправки с одним документом формы?

У меня проблема с вызовом нескольких функций при одном нажатии кнопки submit. У меня есть одна форма, в которую пользователь должен вложить один файл (документ exls), и мне нужно, чтобы один документ использовался для 3 функций. Мне нужно сохранить документ, сделать некоторые действия в pandas и показать его в html. Могу ли я сделать это, поместив его в класс или что-то подобное? Мне очень нужна помощь, спасибо заранее.

def save_exls(request):
    if request.method == 'POST':
        form = DocumentForm(request.POST, request.FILES)
        if form.is_valid():
            newdoc = Document(docfile=request.FILES['docfile'])
            newdoc.save()
            return redirect('html_exls')
    else:
        form = DocumentForm()
    documents = Document.objects.all()
    context = {'documents': documents, 'form': form,}
    return render(request, 'list.html', context)


def pandas_exls(request):
    if request.method == "POST":
        form = DocumentForm(request.POST, request.FILES)
        if form.is_valid():
            output = io.BytesIO()
            newdoc = request.FILES['docfile']
            dfs = pd.read_excel(newdoc, sheet_name=None, index_col=[0])
            writer = pd.ExcelWriter(output)
            for name, df in dfs.items():
                #pandas stuff
                done.to_excel(writer, sheet_name=name)
            output.seek(0)
            response = HttpResponse(
                output, content_type='application/vnd.openxmlformats-officedocument.spreadsheetml.sheet')
            response['Content-Disposition'] = 'attachment; filename=%s' % filename
            return response
    else:
        form = DocumentForm()
    return render(request, 'list.html', {'form': form})


def html_exls(request):
    if request.method == "POST":
        form = DocumentForm(request.POST, request.FILES)
        if form.is_valid():
            output = io.BytesIO()
            newdoc = request.FILES['docfile']
            dfs = pd.read_excel(newdoc, sheet_name=None, index_col=[0])
            writer = pd.ExcelWriter(output)
            for name, df in dfs.items():
                #pandas stuff for html 
                done.to_excel(writer, sheet_name=name)

            html = done.to_html()
            print(html)
            output.seek(0)
            response = HttpResponse(
                output, content_type='application/vnd.openxmlformats-officedocument.spreadsheetml.sheet')
            response['Content-Disposition'] = 'attachment; filename=%s' % filename
            return response
    else:
        form = DocumentForm()
    return render(request, 'list.html', {'form': form})

Некоторые варианты, которые вы, возможно, захотите изучить:

  1. Если все API действительно связаны друг с другом, вы можете преобразовать их в один API, который будет выполнять все 3 функции. Затем, чтобы по-прежнему поддерживать каждый API по отдельности, рефакторить код так, чтобы не повторять один и тот же код в объединенном API вместе с отдельными API.
  2. .
  3. Поверх шаблона HTML добавьте JavaScript (AJAX), который перехватит отправку формы, где вы будете выполнять 3x HTTP POST запросы к различным URL.
  4. Примените шаблон "Публикация/Подписка" (Pub/Sub) (Producer/Consumer). Идея состоит в том, чтобы подписать 3x URL на resource-x. Теперь опубликуйте/поместите данные на ресурс x. Затем система Pub/Sub должна переслать данные и вызвать всех подписанных потребителей, которые являются 3x URL.
    • Одним из способов является использование таких сервисов, как AWS SNS, где вы создаете тему, подписываете 3x URL на эту тему, а затем изменяете свою форму для публикации в этой теме.
    • Другим способом является реализация очереди задач, например Celery. Преобразуйте 3x URL в задачи Celery. Затем подготовьте один HTTP URL, который будет регистрировать полученные запросы к 3x задачам. Затем измените вашу форму, чтобы она отправляла запросы на этот HTTP URL.
  5. Не рекомендуется. Это было бы проще всего, но это грязный хак и очень синхронный. Цепляйте каждое представление друг к другу таким образом, чтобы после завершения работы одного представления вызывать следующее.
Вернуться на верх