Django在POST请求后设置表单字段

HTF*_*HTF 6 django

我正在使用基于类的视图(FormView),我希望在提交表单后保留搜索关键字(POST请求).我在form_valid方法中尝试了这个:

def form_valid(self, form):
        self.initial['search'] = form.data['search']
        ...
Run Code Online (Sandbox Code Playgroud)

但这将为所有用户显示.这是许多网络搜索表单(更不用说谷歌搜索)的常见解决方案,所以我想知道如何在Django中完成这项工作.

更新:2017年6月19日星期一13:18:42 UTC

基于下面的一些答案,我将不得不重新解释我的问题.

我有一个带有几个输入字段的简单表单,在提交表单后,它将查询其他网站以根据搜索字词获得结果.我想将一些结果存储到数据库中,主要是为了生成统计数据,用选定的字段重新显示表单并显示结果.

目前,数据驻留在一个类对象上,并从POST传递给GET.出于明显的安全原因,这不是一个好的解决方案:

class SearchView(FormView):
    ...
    data = dict()

    def form_valid(self, form):
        ....
        self.data['results'] = results

    def get_context_data(self, **kwargs):
        context = super(IndexView, self).get_context_data(**kwargs)
        context['data'] = self.data.pop('results', None)
        return context
Run Code Online (Sandbox Code Playgroud)

题:

在同一页面上显示表单(包含所选字段)和结果的最佳方法是什么,最好不使用会话或在POST和GET之间将它们存储在数据库中.

我已经考虑过的要点:

  1. 不要重定向用户(立即使用当前上下文呈现模板,而我们仍然有响应对象) - 我不喜欢页面刷新将重新提交表单的事实.

  2. 将响应保存到像Redis这样的键值存储中,并将用户重定向到结果/ {result_id},我们可以从数据库中检索响应以预先填充表单中的数据并显示结果 - 这听起来很合理但我为了将结果从POST传递给GET,我们必须添加另一个组件.

  3. 对这种类型的表单使用GET - 我的理解是我们应该使用POST进行数据修改

Sar*_*iev 5

谷歌和其他类似的搜索使用GET参数来传递查询字符串

例子:

  1. 谷歌 test
  2. 结果网址将是 https://www.google.ru/?q=test

所以基本上你需要使用相同的方法并将搜索字符串作为GET参数传递。

这是一般的想法

class SearchView(View):
    success_url = reverse('result-view')

    def get_success_url(self):
        success_url = super().get_success_url()
        return '{0}?search={1}'.format(success_url, self.form.cleaned_data['search'])
    ...

class ResultView(View):
    def get(self, request, *args, **kwargs):
        search_string = request.GET.get('search', '')
Run Code Online (Sandbox Code Playgroud)


Smi*_*ris 3

您没有明确说明要将关键字存储多长时间。

如果只是这样的响应,只要您正确呈现表单,关键字仍然会在那里:

>>> from django import forms
>>> class MyForm(forms.Form):
...     search = forms.CharField()
...
>>> f = MyForm(data={'search': 'KEYWORD'})
>>> print(f['search'])
<input id="id_search" name="search" type="text" value="KEYWORD" />
Run Code Online (Sandbox Code Playgroud)

如果您想在请求中保留关键字但仅针对该用户,请使用会话框架:

def form_valid(self, form):
    self.request.session['search'] = form.data['search']
    ...

def get_form(self, form_class):
    form = super(self, YourView).get_form(form_class)
    form.initial['search'] = self.request.session.get('search', '')
    return form
Run Code Online (Sandbox Code Playgroud)