mirror of
				https://github.com/encode/django-rest-framework.git
				synced 2025-11-04 18:08:03 +03:00 
			
		
		
		
	Merge pull request #2595 from k4nar/fix_url_path
Fix url_path on dynamic routes for inherited viewsets. Fix #2583
This commit is contained in:
		
						commit
						90f1c04c6b
					
				| 
						 | 
					@ -171,9 +171,9 @@ class SimpleRouter(BaseRouter):
 | 
				
			||||||
                # Dynamic detail routes (@detail_route decorator)
 | 
					                # Dynamic detail routes (@detail_route decorator)
 | 
				
			||||||
                for httpmethods, methodname in detail_routes:
 | 
					                for httpmethods, methodname in detail_routes:
 | 
				
			||||||
                    method_kwargs = getattr(viewset, methodname).kwargs
 | 
					                    method_kwargs = getattr(viewset, methodname).kwargs
 | 
				
			||||||
                    url_path = method_kwargs.pop("url_path", None) or methodname
 | 
					 | 
				
			||||||
                    initkwargs = route.initkwargs.copy()
 | 
					                    initkwargs = route.initkwargs.copy()
 | 
				
			||||||
                    initkwargs.update(method_kwargs)
 | 
					                    initkwargs.update(method_kwargs)
 | 
				
			||||||
 | 
					                    url_path = initkwargs.pop("url_path", None) or methodname
 | 
				
			||||||
                    ret.append(Route(
 | 
					                    ret.append(Route(
 | 
				
			||||||
                        url=replace_methodname(route.url, url_path),
 | 
					                        url=replace_methodname(route.url, url_path),
 | 
				
			||||||
                        mapping=dict((httpmethod, methodname) for httpmethod in httpmethods),
 | 
					                        mapping=dict((httpmethod, methodname) for httpmethod in httpmethods),
 | 
				
			||||||
| 
						 | 
					@ -184,9 +184,9 @@ class SimpleRouter(BaseRouter):
 | 
				
			||||||
                # Dynamic list routes (@list_route decorator)
 | 
					                # Dynamic list routes (@list_route decorator)
 | 
				
			||||||
                for httpmethods, methodname in list_routes:
 | 
					                for httpmethods, methodname in list_routes:
 | 
				
			||||||
                    method_kwargs = getattr(viewset, methodname).kwargs
 | 
					                    method_kwargs = getattr(viewset, methodname).kwargs
 | 
				
			||||||
                    url_path = method_kwargs.pop("url_path", None) or methodname
 | 
					 | 
				
			||||||
                    initkwargs = route.initkwargs.copy()
 | 
					                    initkwargs = route.initkwargs.copy()
 | 
				
			||||||
                    initkwargs.update(method_kwargs)
 | 
					                    initkwargs.update(method_kwargs)
 | 
				
			||||||
 | 
					                    url_path = initkwargs.pop("url_path", None) or methodname
 | 
				
			||||||
                    ret.append(Route(
 | 
					                    ret.append(Route(
 | 
				
			||||||
                        url=replace_methodname(route.url, url_path),
 | 
					                        url=replace_methodname(route.url, url_path),
 | 
				
			||||||
                        mapping=dict((httpmethod, methodname) for httpmethod in httpmethods),
 | 
					                        mapping=dict((httpmethod, methodname) for httpmethod in httpmethods),
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -302,12 +302,16 @@ class DynamicListAndDetailViewSet(viewsets.ViewSet):
 | 
				
			||||||
        return Response({'method': 'link2'})
 | 
					        return Response({'method': 'link2'})
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					class SubDynamicListAndDetailViewSet(DynamicListAndDetailViewSet):
 | 
				
			||||||
 | 
					    pass
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
class TestDynamicListAndDetailRouter(TestCase):
 | 
					class TestDynamicListAndDetailRouter(TestCase):
 | 
				
			||||||
    def setUp(self):
 | 
					    def setUp(self):
 | 
				
			||||||
        self.router = SimpleRouter()
 | 
					        self.router = SimpleRouter()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    def test_list_and_detail_route_decorators(self):
 | 
					    def _test_list_and_detail_route_decorators(self, viewset):
 | 
				
			||||||
        routes = self.router.get_routes(DynamicListAndDetailViewSet)
 | 
					        routes = self.router.get_routes(viewset)
 | 
				
			||||||
        decorator_routes = [r for r in routes if not (r.name.endswith('-list') or r.name.endswith('-detail'))]
 | 
					        decorator_routes = [r for r in routes if not (r.name.endswith('-list') or r.name.endswith('-detail'))]
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        MethodNamesMap = namedtuple('MethodNamesMap', 'method_name url_path')
 | 
					        MethodNamesMap = namedtuple('MethodNamesMap', 'method_name url_path')
 | 
				
			||||||
| 
						 | 
					@ -336,3 +340,9 @@ class TestDynamicListAndDetailRouter(TestCase):
 | 
				
			||||||
            else:
 | 
					            else:
 | 
				
			||||||
                method_map = 'get'
 | 
					                method_map = 'get'
 | 
				
			||||||
            self.assertEqual(route.mapping[method_map], method_name)
 | 
					            self.assertEqual(route.mapping[method_map], method_name)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    def test_list_and_detail_route_decorators(self):
 | 
				
			||||||
 | 
					        self._test_list_and_detail_route_decorators(DynamicListAndDetailViewSet)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    def test_inherited_list_and_detail_route_decorators(self):
 | 
				
			||||||
 | 
					        self._test_list_and_detail_route_decorators(SubDynamicListAndDetailViewSet)
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
		Loading…
	
		Reference in New Issue
	
	Block a user