Fixed #25905 -- Prevented leading slashes in urljoin() calls
Leading slashes in the second urljoin argument will return exactly that argument, breaking FileSystemStorage.url behavior if called with a parameter with leading slashes. Also added test cases for null bytes and None. Thanks to Markus for help and review.
This commit is contained in:
parent
b7ea494d65
commit
fdf5cd3429
|
@ -405,7 +405,10 @@ class FileSystemStorage(Storage):
|
||||||
def url(self, name):
|
def url(self, name):
|
||||||
if self.base_url is None:
|
if self.base_url is None:
|
||||||
raise ValueError("This file is not accessible via a URL.")
|
raise ValueError("This file is not accessible via a URL.")
|
||||||
return urljoin(self.base_url, filepath_to_uri(name))
|
url = filepath_to_uri(name)
|
||||||
|
if url is not None:
|
||||||
|
url = url.lstrip('/')
|
||||||
|
return urljoin(self.base_url, url)
|
||||||
|
|
||||||
def accessed_time(self, name):
|
def accessed_time(self, name):
|
||||||
warnings.warn(
|
warnings.warn(
|
||||||
|
|
|
@ -399,11 +399,24 @@ class FileStorageTests(TestCase):
|
||||||
# like encodeURIComponent() JavaScript function do
|
# like encodeURIComponent() JavaScript function do
|
||||||
self.assertEqual(self.storage.url(r"""~!*()'@#$%^&*abc`+ =.file"""),
|
self.assertEqual(self.storage.url(r"""~!*()'@#$%^&*abc`+ =.file"""),
|
||||||
"""/test_media_url/~!*()'%40%23%24%25%5E%26*abc%60%2B%20%3D.file""")
|
"""/test_media_url/~!*()'%40%23%24%25%5E%26*abc%60%2B%20%3D.file""")
|
||||||
|
self.assertEqual(self.storage.url("""ab\0c"""), """/test_media_url/ab%00c""")
|
||||||
|
|
||||||
# should translate os path separator(s) to the url path separator
|
# should translate os path separator(s) to the url path separator
|
||||||
self.assertEqual(self.storage.url("""a/b\\c.file"""),
|
self.assertEqual(self.storage.url("""a/b\\c.file"""),
|
||||||
"""/test_media_url/a/b/c.file""")
|
"""/test_media_url/a/b/c.file""")
|
||||||
|
|
||||||
|
# #25905: remove leading slashes from file names to prevent unsafe url output
|
||||||
|
self.assertEqual(self.storage.url("/evil.com"), "/test_media_url/evil.com")
|
||||||
|
self.assertEqual(self.storage.url(r"\evil.com"), "/test_media_url/evil.com")
|
||||||
|
self.assertEqual(self.storage.url("///evil.com"), "/test_media_url/evil.com")
|
||||||
|
self.assertEqual(self.storage.url(r"\\\evil.com"), "/test_media_url/evil.com")
|
||||||
|
|
||||||
|
self.assertEqual(self.storage.url(None), "/test_media_url/")
|
||||||
|
|
||||||
|
def test_base_url(self):
|
||||||
|
"""
|
||||||
|
File storage returns a url even when its base_url is unset or modified.
|
||||||
|
"""
|
||||||
self.storage.base_url = None
|
self.storage.base_url = None
|
||||||
with self.assertRaises(ValueError):
|
with self.assertRaises(ValueError):
|
||||||
self.storage.url('test.file')
|
self.storage.url('test.file')
|
||||||
|
|
Loading…
Reference in New Issue