-
Notifications
You must be signed in to change notification settings - Fork 3.5k
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
Replace Uri.js with urijs npm module #9740
Conversation
Thanks for the pull request @ebogo1!
Reviewers, don't forget to make sure that:
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
For reference, the urijs docs.
Source/Core/Resource.js
Outdated
|
||
resource._url = uri.resolve(new Uri(getAbsoluteUri(this._url))).toString(); | ||
if (uri.is("urn")) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
URI.absoluteTo()
throws an exception when trying to concatenate URNs, whereas Uri.js returned the unchanged URN. Is this the correct behavior for Resource
? There are a couple other places where this came up.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Where exactly are the urn
urls coming from?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It's possible in .gltf and .czml files, i.e. the images
in https://github.com/CesiumGS/cesium/blob/main/Specs/Data/Models/GltfLoader/BoxTextured/glTF-Embedded/BoxTextured.gltf, used in -
cesium/Specs/Scene/GltfLoaderSpec.js
Line 48 in 1837859
"./Data/Models/GltfLoader/BoxTextured/glTF-Embedded/BoxTextured.gltf"; |
Not sure how common this is, but it does happen in specs at the very least..
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I thought data uris were different than urn?
According to https://stackoverflow.com/a/28865747 urn's start with urn:
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yeah, there's definitely confusion here. almost everything is an urn.. so I'm not sure what differentiates from data uri or other in is
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
On second thought, I don't think just checking for data uris is enough - ModelOutlineLoaderSpec
catches cases in Resource.getDerivedResource where the scheme is "blob"
. The third party Uri.js in main
ignores the base URL's properties (including scheme) if the relative URL has them set:
cesium/Source/ThirdParty/Uri.js
Lines 177 to 182 in 1837859
if (this.scheme) { | |
uri.scheme = this.scheme; | |
uri.authority = this.authority; | |
uri.path = this.path; | |
uri.query = this.query; | |
} else { |
Sandcastles and specs pass if everywhere that (incorrectly) checks Uri.is("urn")
is changed to Uri.scheme() === ""
. This happens in RequestScheduler.getServerKey
, Resource.getDerivedResource
, and getAbsoluteUri
. Is checking just for data schemes as opposed to checking for any scheme before calling Uri.absoluteTo
preferable anywhere? Checking for any scheme at all is more faithful to the behavior in main
.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
So what is the behavior for these urls in main
? Do we just do nothing and return the original url? If so, then we can do the same thing here for now, but it could ultimately be masking a bug. Like should we be trying to absolutize or otherwise manipulate a opaque URL at all?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
And wouldn't is("relative")
be what we would want to check instead?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It's basically the same check under the hood, but much clearer that we are only doing certain things for relative paths
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Do we just do nothing and return the original url?
Yes, this is what the current third party Uri.js does.
And wouldn't is("relative") be what we would want to check instead?
Not quite, since doing so falsely flags urls like "test.png"
, which causes spec failures. In main, new Uri("test.png").resolve(new Uri("http://localhost:8080/Specs/SpecRunner.html"))
turns into "http://localhost:8080/Specs/test.png"
. This is consistent with this npm module's absoluteTo
.
Source/Core/getAbsoluteUri.js
Outdated
} | ||
var url = relativeUri.absoluteTo(base).toString(); | ||
// URI.absoluteTo() escapes the placeholders. Undo that. | ||
url = url.replace(/%7B/g, "{").replace(/%7D/g, "}"); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This code was copied from Resource.prototype.getUrlComponent()
; it's needed because the urijs
implementation of absoluteTo
normalizes URLs (this is also consistent with the URL(relative, base)
constructor in JS. Is this logic safe here?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We switched to absoluteTo
in a unch of other places as well, why is this the only one that we needed this extra workaround for?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This was a weird case that got caught by this line in specs -
getAbsoluteUri("made/up/tms/server/{z}/{x}/{reverseY}.jpg") |
I don't think it's needed for any other reason..
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It almost feels like this fix is in the wrong place, like the calling code is the thing that should be handling {
or perhaps a specialized function like getAbsoluteTemplateStringUri.js
Feels weird to just have something as generic as getAbsoluteUri
embed code like this.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I moved the string replace to the spec in question. Is there no risk of of this mattering at runtime because browsers treat encoded symbols the same as unencoded ones?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I didn't realize the specs were the only place this happens.. did you verify any sandcastles using template uris for imager work?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I verified that imagery Sandcastles work as expected, though there are bunch of Failed to obtain image tile X ... Y: ... Level: ...
in the console.. this happens in the same way in main
, doesn't seem like we have an open issue for it?
As far as I can tell only the spec calls getAbsoluteUri
with a templated url - by the time the imagery urls make their way to fetchImage
the template values are already string replaced correctly.
|
||
describe("Core/buildModuleUrl", function () { | ||
it("produces an absolute URL for a module", function () { | ||
var url = buildModuleUrl("Workers/transferTypedArrayTest.js"); | ||
|
||
expect(url).toMatch(/Workers\/transferTypedArrayTest.js$/); | ||
expect(new Uri(url).isAbsolute()).toBe(true); | ||
var uri = new URI(url); | ||
expect(uri.scheme().length).toBeGreaterThan(0); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
urijs
does not have an equivalent isAbsolute()
function so I checked the scheme and fragment manually per the old Uri.js implementation. This change happens again in TaskProcessor
.
Source/Scene/CreditDisplay.js
Outdated
@@ -521,8 +521,8 @@ function getDefaultCredit() { | |||
logo.indexOf("https://") !== 0 && | |||
logo.indexOf("data:") !== 0 | |||
) { | |||
var logoUrl = new Uri(logo); | |||
logo = logoUrl.getPath(); | |||
var logoUrl = new URI(logo); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This code is never reached by specs..
Straight from their README
What missing features are forcing us to use urljs (or any third party for that matter) instead of just using URL and URLSearchParams? |
@ebogo1 you please merge in |
@mramato Maybe it should be a follow-up to replace the npm module with stock URL? |
That doesn't sound quite right.
MDN specifically mentioned you can just use the All this being said, if this is a stop gap and we plan on taking a serious look into using stock URL post release, then I won't hold things up. It could also affect things like Node.js support. But in general it sounds like we assumed too much or gave up to early in trying to use the standard. |
Pushed a change in ca6a116 to replace |
This should not be merged until #9706 is in
main
.Part of #9473. This code touches a lot of important files and there were a few things that came up; see my review comments.