diff options
| -rw-r--r-- | CHANGES.txt | 6 | ||||
| -rw-r--r-- | TODO.txt | 2 | ||||
| -rw-r--r-- | docs/api/request.rst | 10 | ||||
| -rw-r--r-- | docs/api/url.rst | 4 | ||||
| -rw-r--r-- | pyramid/tests/test_url.py | 66 | ||||
| -rw-r--r-- | pyramid/url.py | 54 |
6 files changed, 131 insertions, 11 deletions
diff --git a/CHANGES.txt b/CHANGES.txt index 90945105f..9b81ad526 100644 --- a/CHANGES.txt +++ b/CHANGES.txt @@ -75,9 +75,11 @@ Features - Better Mako rendering exceptions via ``pyramid.mako_templating.MakoRenderingException`` -- New request methods: ``current_route_url``, ``current_route_path``. +- New request methods: ``current_route_url``, ``current_route_path``, and + ``static_path``. -- New function in ``pyramid.url``: ``current_route_path``. +- New functions in ``pyramid.url``: ``current_route_path`` and + ``static_path``. Internal -------- @@ -11,8 +11,6 @@ Should-Have - Make it possible to use tween aliases in explicit tween config? If not, the tween factories of all add-ons must be APIs. -- "static_path" API (omit host and port)? - Nice-to-Have ------------ diff --git a/docs/api/request.rst b/docs/api/request.rst index c7dc897a3..642e6c84f 100644 --- a/docs/api/request.rst +++ b/docs/api/request.rst @@ -167,16 +167,18 @@ .. automethod:: route_url - .. automethod:: current_route_url - .. automethod:: route_path - .. automethod:: current_route_path + .. automethod:: current_route_url - .. automethod:: resource_url + .. automethod:: current_route_path .. automethod:: static_url + .. automethod:: static_path + + .. automethod:: resource_url + .. attribute:: response_* In Pyramid 1.0, you could set attributes on a diff --git a/docs/api/url.rst b/docs/api/url.rst index 01be76283..131d85806 100644 --- a/docs/api/url.rst +++ b/docs/api/url.rst @@ -13,7 +13,11 @@ .. autofunction:: route_path + .. autofunction:: current_route_path + .. autofunction:: static_url + .. autofunction:: static_path + .. autofunction:: urlencode diff --git a/pyramid/tests/test_url.py b/pyramid/tests/test_url.py index ad55cae0b..6fb67ed5a 100644 --- a/pyramid/tests/test_url.py +++ b/pyramid/tests/test_url.py @@ -305,10 +305,11 @@ class TestURLMethodsMixin(unittest.TestCase): mapper = DummyRoutesMapper(route=route) request.matched_route = route request.matchdict = {} + request.script_name = '/script_name' request.registry.registerUtility(mapper, IRoutesMapper) result = request.current_route_path('extra1', 'extra2', _query={'a':1}, _anchor=u"foo") - self.assertEqual(result, '/1/2/3/extra1/extra2?a=1#foo') + self.assertEqual(result, '/script_name/1/2/3/extra1/extra2?a=1#foo') def test_route_path_with_elements(self): from pyramid.interfaces import IRoutesMapper @@ -372,6 +373,49 @@ class TestURLMethodsMixin(unittest.TestCase): self.assertEqual(info.args, ('pyramid.tests:static/foo.css', request, {}) ) + def test_static_path_abspath(self): + request = self._makeOne() + self.assertRaises(ValueError, request.static_path, '/static/foo.css') + + def test_static_path_found_rel(self): + from pyramid.interfaces import IStaticURLInfo + request = self._makeOne() + request.script_name = '/foo' + info = DummyStaticURLInfo('abc') + request.registry.registerUtility(info, IStaticURLInfo) + result = request.static_path('static/foo.css') + self.assertEqual(result, 'abc') + self.assertEqual(info.args, + ('pyramid.tests:static/foo.css', request, + {'_app_url':'/foo'}) + ) + + def test_static_path_abs(self): + from pyramid.interfaces import IStaticURLInfo + request = self._makeOne() + request.script_name = '/foo' + info = DummyStaticURLInfo('abc') + request.registry.registerUtility(info, IStaticURLInfo) + result = request.static_path('pyramid.tests:static/foo.css') + self.assertEqual(result, 'abc') + self.assertEqual(info.args, + ('pyramid.tests:static/foo.css', request, + {'_app_url':'/foo'}) + ) + + def test_static_path(self): + from pyramid.interfaces import IStaticURLInfo + request = self._makeOne() + request.script_name = '/foo' + info = DummyStaticURLInfo('abc') + request.registry.registerUtility(info, IStaticURLInfo) + result = request.static_path('static/foo.css') + self.assertEqual(result, 'abc') + self.assertEqual(info.args, + ('pyramid.tests:static/foo.css', request, + {'_app_url':'/foo'}) + ) + class Test_route_url(unittest.TestCase): def _callFUT(self, route_name, request, *elements, **kw): from pyramid.url import route_url @@ -458,6 +502,26 @@ class Test_static_url(unittest.TestCase): self.assertEqual(request.path, 'abc') self.assertEqual(request.kw, {'_app_url':''}) +class Test_static_path(unittest.TestCase): + def _callFUT(self, path, request, **kw): + from pyramid.url import static_path + return static_path(path, request, **kw) + + def _makeRequest(self): + class Request(object): + def static_path(self, path, **kw): + self.path = path + self.kw = kw + return 'static path' + return Request() + + def test_it(self): + request = self._makeRequest() + result = self._callFUT('abc', request, _anchor='anchor') + self.assertEqual(result, 'static path') + self.assertEqual(request.path, 'abc') + self.assertEqual(request.kw, {'_anchor':'anchor'}) + class Test_current_route_url(unittest.TestCase): def _callFUT(self, request, *elements, **kw): from pyramid.url import current_route_url diff --git a/pyramid/url.py b/pyramid/url.py index 77647fcf8..1f353a4b9 100644 --- a/pyramid/url.py +++ b/pyramid/url.py @@ -368,8 +368,47 @@ class URLMethodsMixin(object): return info.generate(path, self, **kw) - def current_route_url(self, *elements, **kw): + def static_path(self, path, **kw): + """ + Generates a path (aka a 'relative URL', a URL minus the host, scheme, + and port) for a static resource. + + This function accepts the same argument as + :meth:`pyramid.request.Request.current_static_url` and performs the + same duty. It just omits the host, port, and scheme information in + the return value; only the script_name, path, query parameters, and + anchor data are present in the returned string. + + Example:: + + request.static_path('mypackage:static/foo.css') => + + /static/foo.css + + .. note:: Calling ``request.static_path(apath)`` is the same + as calling ``request.static_url(apath, + _app_url=request.script_name)``. + :meth:`pyramid.request.Request.static_path` is, in fact, + implemented in terms of + `:meth:`pyramid.request.Request.static_url` in just this + way. As a result, any ``_app_url`` passed within the ``**kw`` + values to ``static_path`` will be ignored. + """ + if os.path.isabs(path): + raise ValueError('Absolute paths cannot be used to generate static ' + 'urls (use a package-relative path or an asset ' + 'specification).') + if not ':' in path: + # if it's not a package:relative/name and it's not an + # /absolute/path it's a relative/path; this means its relative + # to the package in which the caller's module is defined. + package = caller_package() + path = '%s:%s' % (package.__name__, path) + + kw['_app_url'] = self.script_name + return self.static_url(path, **kw) + def current_route_url(self, *elements, **kw): """ Generates a fully qualified URL for a named :app:`Pyramid` :term:`route configuration` based on the 'current route'. @@ -456,7 +495,7 @@ class URLMethodsMixin(object): way. As a result, any ``_app_url`` passed within the ``**kw`` values to ``current_route_path`` will be ignored. """ - kw['_app_url'] = '' + kw['_app_url'] = self.script_name return self.current_route_url(*elements, **kw) @@ -512,6 +551,17 @@ def static_url(path, request, **kw): """ return request.static_url(path, **kw) +def static_path(path, request, **kw): + """ + This is a backwards compatibility function. Its result is the same as + calling:: + + request.static_path(path, **kw) + + See :meth:`pyramid.request.Request.static_path` for more information. + """ + return request.static_path(path, **kw) + def current_route_url(request, *elements, **kw): """ This is a backwards compatibility function. Its result is the same as |
