Sunday, October 29, 2017

Re: Building a search form with 4 required choices, which will be inserted as arguments in an URL [warning: long question]

That makes much more sense.  It's my fault for not reading the Django docs properly, but I don't seem to soak in the concepts at all by simply reading.  

I went with a ListView + get_queryset override.  I haven't managed to get the filter to work but the search itself is working properly.

Thanks Daniel!

On Sunday, October 29, 2017 at 7:59:25 AM UTC-4, Daniel Roseman wrote:
On Monday, 23 October 2017 16:59:36 UTC+1, Jack wrote:
This is a semi-long question.  Please let me know wherever I make a mistake.

I'm building a search form with 4 required choices, 1 of the choices is a CharField with a max_length of 3.  The other 3 choices are ChoiceField's.  Here is a picture of what the search form looks like:


I've read through the Django docs and other things on the Internet but I'm still very unclear about how to approach this.

1. First I believe I need to create 4 args or kwargs in the url for each of the choices.  If I use args, it would look something like...

url(r'^search?(\w+{3})&(\w+{2})&(\w+{1-2})&(\w+{1-2})', function/class view, name='search')

2. Next, I need to pass the user's input in the html page into the url args.  I have a form set up to get the user's input.  But how would I write this on the HTML page?  Do I simply make a url tag like {% url 'search' args1, args2, args3, args4 %}?

3. Then I need to create the views function.  My first question is, should I use a function-based view or the generic class-based ListView?  The result of the search will be a list of items, so ListView is a good template to use, but I don't know how having 4 args would affect using ListView.  My second question is, what is the most effective way of making this search?  I need to check if any records in the database matches the user's search, so would I do something like 'For record in database' to check over every record in the database?

If I used a function view, would it look something like:

def search(request, args1, args2, args3, args4):
     for record in database:
          if args matches record:
               display record

Thank you for reading through the question


Your difficulties all stem from the same misunderstanding here.

Forms - at least when using the GET action - put their arguments in the querystring - the bit after the ? in the URL. Django doesn't treat that as part of the URL itself, but as a separate attribute, `request.GET`. So both your first and second questions are irrelevant: you don't need to capture the values in a URL pattern, and nor do you need to insert them in there in the HTML somehow. Just use a basic pattern of `r('^search/$)` and all will be fine.

For your third question, it makes no difference whether you use function or class-based views. If you did use a ListView, though, you could override `get_queryset` to filter by the values in the GET dictionary:

def get_queryset(self):
    qs = super(MyListView, self).get_queryset()
    if 'bedrooms' in request.GET:
        qs = qs.filter(bedrooms=request.GET['bedrooms']
    ... etc ...
    return qs

-- 
DR.

--
You received this message because you are subscribed to the Google Groups "Django users" group.
To unsubscribe from this group and stop receiving emails from it, send an email to django-users+unsubscribe@googlegroups.com.
To post to this group, send email to django-users@googlegroups.com.
Visit this group at https://groups.google.com/group/django-users.
To view this discussion on the web visit https://groups.google.com/d/msgid/django-users/c6bb83c1-16fd-4375-88ba-9516a9677c29%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

No comments:

Post a Comment