Skip to content

Commit 55eb8e7

Browse files
committed
Fix path normalization.
- Port remove_dot_segments from jsonld.js. - Fixes RFC 3984 tests.
1 parent 72be24c commit 55eb8e7

File tree

1 file changed

+50
-10
lines changed

1 file changed

+50
-10
lines changed

lib/pyld/jsonld.py

Lines changed: 50 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -515,16 +515,9 @@ def prepend_base(base, iri):
515515

516516
transform['query'] = rel.query
517517

518-
# normalize path
519-
path = transform['path']
520-
add_slash = path.endswith('/')
521-
path = posixpath.normpath(path)
522-
if not path.endswith('/') and add_slash:
523-
path += '/'
524-
# do not include '.' path
525-
if path == '.':
526-
path = ''
527-
transform['path'] = path
518+
if rel.path != '':
519+
# normalize path
520+
transform['path'] = remove_dot_segments(transform['path'])
528521

529522
transform['fragment'] = rel.fragment
530523

@@ -581,6 +574,53 @@ def remove_base(base, iri):
581574
return unparse_url((None, None, path, rel.query, rel.fragment)) or './'
582575

583576

577+
def remove_dot_segments(path):
578+
"""
579+
Removes dot segments from a URL path.
580+
581+
:param path: the path to remove dot segments from.
582+
583+
:return: a path with normalized dot segments.
584+
"""
585+
586+
# RFC 3984 5.2.4 (reworked)
587+
588+
# empty path shortcut
589+
if len(path) == 0:
590+
return ''
591+
592+
input = path.split('/')
593+
output = []
594+
595+
while len(input) > 0:
596+
next = input.pop(0)
597+
done = len(input) == 0
598+
599+
if next == '.':
600+
if done:
601+
# ensure output has trailing /
602+
output.append('')
603+
continue
604+
605+
if next == '..':
606+
if len(output) > 0:
607+
output.pop()
608+
if done:
609+
# ensure output has trailing /
610+
output.append('')
611+
continue
612+
613+
output.append(next)
614+
615+
# ensure output has leading /
616+
if len(output) > 0 and output[0] != '':
617+
output.insert(0, '')
618+
if len(output) is 1 and output[0] == '':
619+
return '/'
620+
621+
return '/'.join(output)
622+
623+
584624
ParsedUrl = namedtuple(
585625
'ParsedUrl', ['scheme', 'authority', 'path', 'query', 'fragment'])
586626

0 commit comments

Comments
 (0)