How to reverse_lazy to a view/url with variable?

12,835

Solution 1

As Nickie suggested in the comments: https://docs.djangoproject.com/en/1.11/ref/class-based-views/mixins-editing/#django.views.generic.edit.DeletionMixin.success_url

Solved this with success_url = "/farm/{farm_id}"

Solution 2

Yes, you can do this with success_url in this way:

class DeleteAssignment(DeleteView):
    . . . . . 
    . . . . . 

    . . . . . 
    def get_success_url(self):
          # if you are passing 'pk' from 'urls' to 'DeleteView' for company
          # capture that 'pk' as companyid and pass it to 'reverse_lazy()' function
          companyid=self.kwargs['pk']
          return reverse_lazy('company', kwargs={'pk': companyid})

This should work perfectly.

Share:
12,835
Jon
Author by

Jon

Political Junkie, Podcast Addict, Software Developer, & East Coast Refugee

Updated on June 04, 2022

Comments

  • Jon
    Jon almost 2 years

    I've got a DeleteView I use for removing objects from a model. It is launched via a button in a table. It works fine.

    class DeleteAssignment(DeleteView):
      model = Assignment
      success_url = reverse_lazy('company')
    

    Screenshot

    I just want to have it return to it's parent view on success. I currently have it redirecting to the parent's parent (company), as this view doesn't require a variable. This would be simple, but the parent view requires a variable farm_id to render, this is captured from the url like "/farm/18"

    url(r'^farm/(?P<farm_id>.+)', views.farm, name='farm'),
    

    I've solved this with forms on the page by having them redirect to the view farm with the variable farm_id.

    return redirect(farm, farm_id=farm_id)
    

    How could I do this with the success_url for my DeleteView?

    Example for nickie:

    views.py

     @login_required
        def farm(request, farm_id=None):
            user = request.user
            company_id = user.profile.company_id
            farm_id = farm_id
            farm_filter = Farm.objects.filter(farm=farm_id)
            farm_current = farm_filter[0]
            # farm_company =
            serial_filter = Sensor.objects.filter(assignment__farm__company_id__isnull=True)
            assignment_filter = Assignment.objects.filter(farm=farm_id)
            farm_instance = Farm.objects.get(farm=farm_filter[0].farm)
            update_farm_form = UpdateFarmForm(instance=farm_instance)
            assign_sensor_form = AssignmentForm()
    
            if request.method == 'POST' and 'updatefarm' in request.POST:
                update_farm_form = UpdateFarmForm(request.POST, instance=farm_instance)
                if update_farm_form.is_valid():
                    update_farm_form.save()
                    return redirect(farm, farm_id=farm_id)
            else:
                if request.method == "POST" and 'assignsensor' in request.POST:
                    assign_sensor_form = AssignmentForm(request.POST)
                    if assign_sensor_form.is_valid():
                        assignment = assign_sensor_form.save()
                        if user.is_staff is True:
                            assignment.company_id = farm_filter[0].company_id
                        else:
                            assignment.company_id = user.profile.company_id
                        assignment.save()
                        return redirect(farm, farm_id=farm_id)
                    else:
                        assign_sensor_form = AssignmentForm(request.POST)
            return render(request, 'users/farm_template.html', {'company_id': company_id, 'farm_filter': farm_filter, 'farm_current': farm_current, 'serial_filter': serial_filter, 'assignment_filter': assignment_filter, 'update_farm_form': update_farm_form, 'assign_sensor_form': assign_sensor_form})
    

    urls.py

    from django.conf.urls import url, include
    from django.contrib.auth import views as auth_views
    
    from apps.dashboard import views
    from apps.dashboard.views import DeleteAssignment, DeleteFarm
    
    urlpatterns = [
        url(r'^company/', views.company_view, name='company'),
        # url(r'^test/', views.test),
        # url(r'^test2/', views.test2, name='test2'),
        # url(r'^farms/', views.add_farms),
        url(r'^manual-signup/', views.signup_manual),
        url(r'^signup/(?P<company_id>.+)', views.signup_company),
        url(r'^settings/', views.update_profile),
        url(r'^create-company/', views.create_company),
        url(r'^create-sensor/', views.create_sensor),
        url(r'^assign-sensor/', views.assign_sensor),
        url(r'^login/$', auth_views.login, {'template_name': 'login.html'}, name='login'),
        url(r'^logout/$', auth_views.logout, {'next_page': '/login'}, name='logout'),
        url(r'^$', views.main),
        # url(r'^company/(?P<company_id>.+)/farm/(?P<farm_id>.+)', views.farm),
        url(r'^farm/(?P<farm_id>.+)', views.farm, name='farm'),
        url(r'^unit/(?P<sensor_id>.+)', views.unit),
        # url(r'^company/(?P<company_id>.+)', views.company),
        url(r'^download/', views.download),
        # url(r'^export/xls/$', views.export_users_xls),
        url(r'^live/', views.live),
        url(r'^data/', views.data),
        url(r'^debug/', views.debug),
        url(r'^delete-assignment/(?P<pk>\d+)/$', DeleteAssignment.as_view(), name='delete-assignment', ),
        url(r'^delete-farm/(?P<pk>\d+)/$', DeleteFarm.as_view(), name='delete-farm', ),
        url(r'^', include('django.contrib.auth.urls'))
    ]
    

    This is view redirects to itself upon successful form submission. This reloads tables based on the user submission without having to deal with js for now.

    The farm_id in return redirect(farm, farm_id=farm_id) is captured from the url, via the appropriate line in urls.py url(r'^farm/(?P<farm_id>.+)', views.farm, name='farm'),

    This is all I want to do with the delete view, instead of the success url simply being a view, a view with a variable like I did above.