Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[SR-13846] URL/URLComponents does not know about path segments. #3239

Open
dhoepfl opened this issue Nov 12, 2020 · 1 comment
Open

[SR-13846] URL/URLComponents does not know about path segments. #3239

dhoepfl opened this issue Nov 12, 2020 · 1 comment

Comments

@dhoepfl
Copy link
Contributor

dhoepfl commented Nov 12, 2020

Previous ID SR-13846
Radar rdar://problem/71330231
Original Reporter @dhoepfl
Type Bug
Additional Detail from JIRA
Votes 0
Component/s Foundation
Labels Bug
Assignee None
Priority Medium

md5: 7c361480bdc90db77c2604de02f281d0

Issue Description:

When using appendPathComponent to add a path segment that contains a slash, behaviour of appendPathComponent and lastPathComponent is inconsistent:

let url = URL(string: "https://example.com/")!
url.appendPathComponent("test/with%escape")
print(url)
print(url.lastPathComponent) 

Actual result:

https://example.com/test/with%25escape
with%escape 

Expected result:

https://example.com/test%2Fwith%25escape
test/with%escape

Escaping the segment using String’s addPercentEncoding with a custom variant of CharacterSet.urlPathAllowed without “/” does not work either:

var myCharset = CharacterSet.urlPathAllowed
myCharset.remove("/")
let component = 
    "test/with%escape".addingPercentEncoding(withAllowedCharacters: myCharset)!

var url = URL(string: "https://example.com/")!
url.appendPathComponent(component)
print(url)
print(url.lastPathComponent)

Results in:

https://example.com/test%252Fwith%2525escape
test%2Fwith%25escape

URLComponents path fails with the same result:

var myCharset = CharacterSet.urlPathAllowed
myCharset.remove("/")

var uc = URLComponents()
uc.scheme = "https"
uc.host = "example.com"
uc.path = "/" +
    "test/with%escape".addingPercentEncoding(withAllowedCharacters: myCharset)!

let url = uc.url!
print(url)
print(url.lastPathComponent)

The only workaround I found was to build the URL string by hand, the using URL(string🙂 This still leaves lastPathComponent incorrect:

var myCharset = CharacterSet.urlPathAllowed
myCharset("/")

var path = 
    "test/with%escape".addingPercentEncoding(withAllowedCharacters: myCharset)!

let url = URL(string: "https://example.com/" + path)!
print(url)
print(url.lastPathComponent)

Resulting in:

https://example.com/test%2Fwith%25escape
with%escape

TL;DR:

  • I guess changing the bahaviour of appendPathComponent to appending one path segment is not an option. But it should be documented that appendPathComponent is not appending a RFC 3986 path segment but a partial path.

  • I think pathComponents and lastPathComponent should be changed: Both must not decode "%2F" before splitting the path.

  • I would love to see appendPathSegment(_ segment: String) on URL.

  • URL’s pathComponents could be settable.

  • URLComponents could include a settable pathSegements.

  • CharacterSet could include a urlPathSegmentAllowed.

@typesanitizer
Copy link

@swift-ci create

@swift-ci swift-ci transferred this issue from apple/swift-issues Apr 25, 2022
@shahmishal shahmishal transferred this issue from apple/swift May 5, 2022
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

2 participants