a better way to do ajax in django

后端 未结 4 1586
情歌与酒
情歌与酒 2020-12-25 08:51

The other day I wrote some AJAX for a Django app that i have been working on.

I come from Ruby on Rails, so I haven\'t done much in the way of raw JS.

So bas

4条回答
  •  粉色の甜心
    2020-12-25 09:54

    I am quite late, but I want to document how to combine and adapt the solutions presented by d0ugal in a way, that it will resolve a much cleaner template-code.

    I have a model representing contact persons.

    The (generic) view to get one ContactPerson looks like this:

    def contcactperson_detail_view(request, name):
        try:
            person = ContactPerson.objects.get(slug=name)
        except:
           raise Http404
        if request.is_ajax():
            return contcactperson_detail_view_ajax(request, person)
        return list_detail.object_detail(
                request,
                queryset = ContactPerson.objects.all(),
                object_id = person.id,
                template_object_name = "contactperson",
            )
    
    @render_to('cms/contactperson_detail_ajax.html')    
    def  contcactperson_detail_view_ajax(request, person):
        return {'contactperson':person, 'is_ajax':True}
    

    The template to render the view that handles one ContactPerson is called contcactperson_detail_view.html:

    {% extends "index.html" %}
    {% block textpane %}
    
    

    {{ contactperson.first_name }} {{ contactperson.family_name }}

     
    {% include 'cms/contactperson_detail_photo.html' %}
    {% include 'cms/contactperson_detail_textpane.html' %}
    {% endblock %}

    It includes two sub-templates

    contactperson_detail_textpane.html
    
    
    

    {{ contactperson.description }}

    • Email
      {{ contactperson.mail }}
    • Contact Person for
        {% for c in contactperson.categories.all %}
      • {{ c }}
      • {% endfor %}

    and contactperson_detail_photo.html

    {% with contactperson.photo.detailphoto as pic %} 
        {% with pic.url as pic_url %}    
        
    {{ i.name }}
    {% endwith %} {% endwith %}

    this 3 templates will be used, if the request isn't ajax.

    But if the request is ajax, contcactperson_detail_view will return the view contcactperson_detail_view_ajax, that uses the template contactperson_detail_ajax.html for rendering. And this template looks like this:

    {{ contactperson.first_name }} {{ contactperson.family_name }}

    {% include 'cms/contactperson_detail_photo.html' %} {% include 'cms/contactperson_detail_textpane.html' %}

    So it uses the same sub-templates but isn't extending anything, therefore only the needed markup delivered. As the ajax view passes is_ajax = True to the template, it can be used to adjust minor things, like setting correct id-attributes.

    No context-processor or additional url-conf needed.

    Finally the Javascript code:

    $("#contact_person_portlet a").click(function(event){
           event.preventDefault();
           $.ajax({
               type: "GET",
               url: event.target.getAttribute('href'),
               success: function(msg){
                   overlay(msg);
               }
            });
        });
    

    Hope that it will be useful for some people. If so, please leave a comment!

提交回复
热议问题