0

Some slightly related questions have been asked about this, but the answers did not really help me. When I tried to implement a potential good hint suggested elsewhere (custom templates), I did not get the desired results.

In my template, I am iterating over a set of keys from a dictionary. The dictionary itself originates from submitting a Django formset.

XML Template snippet: (I am rendering to an XML file)

{% for x in range %}
    <file type="{{ form-'x'-type }}" viewpath="{{ form-'x'-file }}"/>
{% endfor %}

The above obviously does not work. The iteration works. The rangevariable is a python argument corresponding to range(int(request.POST['form-TOTAL_FORM'])) passed from the view to the XML template.

At every iteration in the template, I need {{ form-0-type }}, {{ form-1-type}}, {{ form-2-type }}, etc.

How do I do that? If I really need to use a custom filter for this, how do I do this?

I hope this question (and the answers) will help many having the same problem.

Thanks.

Edit:(Dictionary posted)

<QueryDict: 
{
  u'form-MAX_NUM_FORMS': [u'1000'], 
  u'form-INITIAL_FORMS': [u'0'], 
  u'form-TOTAL_FORMS': [u'2'], 
  u'form-0-type': [u'1'], 
  u'form-1-type': [u'2'], 
  u'csrfmiddlewaretoken': [u'LpkjdDcqRCL4VPM0SAuU7efgZjgeubTN']
}>

Additional note: In a second view, I lookup the values for the foreign keys and put the values in another dictionary, which I send to my XML template.

Snippet of the code that does this:

detailed_request = {}
for x in range(0, int(request.POST['form-TOTAL_FORMS'])):
    detailed_request['form-'+str(x)+'-type'] = Upload_Type.objects.get(pk=request.POST['form-'+ str(x)+'-type'])
    detailed_request['form-'+str(x)+'-file'] = request.FILES['form-'+str(x)+'-file']

The above is a working snippet. When I trace detailed_request, I have all the information I need:

{
  'form-1-type': <Upload_Type: malib>,
  'form-0-type': <Upload_Type: axf_file>
}
Community
  • 1
  • 1
Shailen
  • 7,909
  • 3
  • 29
  • 37
  • If you've got the keys in a dictionary, why can't you iterate over those directly rather than trying to create the names dynamically? – Daniel Roseman Sep 10 '13 at 13:40
  • Thanks for the comment. Well, the dictionary keys are like this: `form-0-type`, `form-1-type` etc. From my template, I am having trouble iterating through those variable dictionary key names. If I could iterate through those variable keys name, the problem would be solved I would say. – Shailen Sep 10 '13 at 13:45
  • I think you should post an example of your dictionary. – Daniel Roseman Sep 10 '13 at 14:00
  • can you not just do `form-{{x}}-type` ? – karthikr Sep 10 '13 at 14:07
  • @karthikr: No, because `form-1-type` is a variable name that is already within a `{{ }}` in the template. Any other suggestions? – Shailen Sep 10 '13 at 14:19
  • how about writing a template tag that would render this snippet for you? – karthikr Sep 10 '13 at 14:20
  • @karthikr: Yes, that was a hint I got from another post (hyperlinked in my post.) Template tags 'appears' to be a solution, but how do I really do that? I am following the custom template official documentation, but I am not sure I am doing the right thing. IF you have an idea, please post a possible template tag snippet as an answer, which I could vote as solution, if it works out :) Thanks! – Shailen Sep 10 '13 at 14:23
  • 1
    before we write a snippet, can you not just put the `form-x-type` into a nested dictionary with a unique key-value pair? That way you can do away with the snippet – karthikr Sep 10 '13 at 14:26
  • By the way, other research suggest using `django-crispy` for iterating `formsets`. I am reading about this at the moment. Do you have experience about that? – Shailen Sep 10 '13 at 14:26
  • @karthikr: I was just doing that actually, before you suggested that :) – Shailen Sep 10 '13 at 14:33
  • @Everybody, using a nested dictionary solved the issue. However, I still think there must be a neater way of iterating formsets in Django. I did feel I was writing a lot of code to do this task, which is unusual in the Django world. Anyway, I'll post my working snippet in a short while. Maybe that can help other people around. – Shailen Sep 10 '13 at 14:47

2 Answers2

0

Just in case somebody has the same problem, I actually changed the way I do things.

I do not iterate the formset in the template. Instead, I implemented the solution from Paolo Bergantino here: Dynamically adding a form to a Django formset with Ajax

Then in my views, I simply get every data I need from request.FILES

I hope that helps anybody who started with the same wrong approach.

Community
  • 1
  • 1
Shailen
  • 7,909
  • 3
  • 29
  • 37
-2

You can access the for loop helper variables through the following variables

forloop.counter   The current iteration of the loop (1-indexed)
forloop.counter0  The current iteration of the loop (0-indexed)

More at: https://docs.djangoproject.com/en/dev/ref/templates/builtins/#for

So you'd do...

{{ form }}-{{ forloop.counter }}-{{ type }}

stormlifter
  • 3,781
  • 3
  • 17
  • 20
  • 1
    That seemed to be almost a good answer, but almost. {{ form-0-type }} corresponds to a value from the dictionary passed from the view. With the proposed solution, the template will try to find the values for `form` and `type` from the arguments passed from the view. – Shailen Sep 10 '13 at 14:00