im stuck with an error of :

Reverse for 'detail' not found. 'detail' is not a valid view function or pattern name.

when i tried to override the AssignTaskView View.

The rationale for doing so is to allow my user to reassign Tasks to others without having to generate a seperate task to do so as well as to put in my custom forms for displaying the lsit of users to choose from.

I have most of my inspirations from this particular post :

Overwrite django view with custom context (Django 1.11, Viewflow)

And here is my code:

url.py

It actually allows me to override and display my own form .

    path('pipeline/<process_pk>/documents/<task_pk>/assign/', OverrideTaskView.as_view(), {
     'flow_class': Pipeline,
     'flow_task': Pipeline.documents
}),

the issue lies here :

views.py

class OverrideTaskView(AssignTaskView,FormView):
form_class=AssignForm

def get_form_kwargs(self):
    kwargs = super(OverrideTaskView, self).get_form_kwargs()
    kwargs.update({'id': self.request.user})
    return kwargs

def get_context_data(self, **kwargs):
    context = super(AssignTaskView, self).get_context_data(**kwargs)
    context['activation'] = self.activation
    return context

def form_valid(self, form):
    if '_assign' or '_continue' in request.POST:
        form.save(commit=False)
        assigned = form.cleaned_data.get('user')
        self.activation.assign(assigned)
        self.success(_('Task {task} has been assigned'))
        return HttpResponseRedirect(self.get_success_url())
    else:
        return self.get(request, *args, **kwargs)

I suspect it has something to do with the get_success_url ? The error only pops up after i click the confirmation button , please help!

edit

This is the URL patterns found from my debug page :

^pipeline/(?P<process_pk>\d+)/documents/(?P<task_pk>\d+)/assign/$ 
[name='documents__assign']
pipeline/ ^archive/$ [name='archive']
pipeline/ ^action/cancel/(?P<process_pk>\d+)/$ [name='action_cancel']
pipeline/ ^(?P<process_pk>\d+)/$ [name='detail']   #<--- its here!!

full error trace back

Internal Server Error: /pipeline/35/documents/195/assign/
Traceback (most recent call last):
  File "C:\Users\Dion Neo Wen Shun\AppData\Local\Programs\Python\Python38\lib\site-packages\django\core\handlers\exception.py", line 34, in inner
    response = get_response(request)
  File "C:\Users\Dion Neo Wen Shun\AppData\Local\Programs\Python\Python38\lib\site-packages\django\core\handlers\base.py", line 115, in _get_response
    response = self.process_exception_by_middleware(e, request)
  File "C:\Users\Dion Neo Wen Shun\AppData\Local\Programs\Python\Python38\lib\site-packages\django\core\handlers\base.py", line 113, in _get_response
    response = wrapped_callback(request, *callback_args, **callback_kwargs)
  File "C:\Users\Dion Neo Wen Shun\AppData\Local\Programs\Python\Python38\lib\site-packages\django\views\generic\base.py", line 71, in view
    return self.dispatch(request, *args, **kwargs)
  File "C:\Users\Dion Neo Wen Shun\AppData\Local\Programs\Python\Python38\lib\site-packages\django\utils\decorators.py", line 43, in _wrapper
    return bound_method(*args, **kwargs)
  File "C:\Users\Dion Neo Wen Shun\AppData\Local\Programs\Python\Python38\lib\contextlib.py", line 75, in inner
    return func(*args, **kwds)
  File "C:\Users\Dion Neo Wen Shun\AppData\Local\Programs\Python\Python38\lib\site-packages\viewflow\decorators.py", line 213, in _wrapper
    return view(request, **kwargs)
  File "C:\Users\Dion Neo Wen Shun\AppData\Local\Programs\Python\Python38\lib\site-packages\viewflow\flow\views\task.py", line 197, in dispatch
    return super(AssignTaskView, self).dispatch(request, *args, **kwargs)
  File "C:\Users\Dion Neo Wen Shun\AppData\Local\Programs\Python\Python38\lib\site-packages\django\views\generic\base.py", line 97, in dispatch
    return handler(request, *args, **kwargs)
  File "C:\Users\Dion Neo Wen Shun\AppData\Local\Programs\Python\Python38\lib\site-packages\viewflow\flow\views\task.py", line 175, in post
    self.success(_('Task {task} has been assigned'))
  File "C:\Users\Dion Neo Wen Shun\AppData\Local\Programs\Python\Python38\lib\site-packages\viewflow\flow\views\mixins.py", line 90, in success
    self.report(message, level=messages.SUCCESS, fail_silently=fail_silently, **kwargs)
  File "C:\Users\Dion Neo Wen Shun\AppData\Local\Programs\Python\Python38\lib\site-packages\viewflow\flow\views\mixins.py", line 69, in report
    process_url = reverse('{}:detail'.format(namespace), args=[self.activation.process.pk])
  File "C:\Users\Dion Neo Wen Shun\AppData\Local\Programs\Python\Python38\lib\site-packages\django\urls\base.py", line 87, in reverse
    return iri_to_uri(resolver._reverse_with_prefix(view, prefix, *args, **kwargs))
  File "C:\Users\Dion Neo Wen Shun\AppData\Local\Programs\Python\Python38\lib\site-packages\django\urls\resolvers.py", line 677, in _reverse_with_prefix
    raise NoReverseMatch(msg)
django.urls.exceptions.NoReverseMatch: Reverse for 'detail' not found. 'detail' is not a valid view function or pattern name.
[08/Apr/2020 22:37:24] "POST /pipeline/35/documents/195/assign/ HTTP/1.1" 500 129534

Im really clueless as to what is happening!

2

There are 2 best solutions below

0
On

to override an assign view, you could pass assign_view_class to the View constructor, ex

flow.View(..., assign_view=MyView.as_view())

Or create a custom node, with assign_view_class attribute redefined - https://github.com/viewflow/viewflow/blob/master/demo/shipment/flows.py#L57

0
On

I tried installing django-extensions and used the show_urls method. This told me that the naming was a little different from the others , for example :

Heres the URL which i overrode:

/pipeline/<process_pk>/documents/<task_pk>/assign/      cash.views.OverrideTaskView     cash:documents__assign

Here is the original URL

/pipeline/<process_pk>/documents/<task_pk>/assign/      viewflow.flow.views.task.AssignTaskView cash:pipeline:documents__assign

hence in my urls.py in my project (not the root url config)

i added in this the the overrode URL

path('pipeline/<process_pk>/documents/<task_pk>/assign/',
    OverrideTaskView.as_view(),
    {'flow_class': Pipeline,
    'flow_task': Pipeline.documents},
    name="pipeline:{}__assign".format(Pipeline.documents.name)),

However this did not solve the issue .

I added a print statement to the custom assign view :

print(self.request.resolver_match.namespace)

and it gave me :

cash

which was wrong as it was supposed to be :

cash:pipeline

Therefore the system was trying to search the URL front the wrong directory? (i assume)

Anyways, I resolved the issue by putting this into the get success url:

    def get_success_url(self):
    """Continue on task or redirect back to task list."""
    url = self.activation.flow_task.get_task_url(
        self.activation.task, url_type='guess', user=self.request.user,
        namespace=self.request.resolver_match.namespace + ':' + 'pipeline')

    back = self.request.GET.get('back', None)
    if back and not is_safe_url(url=back, allowed_hosts={self.request.get_host()}):
        back = '/'

    if '_continue' in self.request.POST and back:
        url = "{}?back={}".format(url, urlquote(back))
    elif back:
        url = back

    return url