And Fantom's Uri class does an excellent job of breaking down a URI string into it's constituent parts. It also does a darn good job of encoding / decoding the different syntax parts too (this ticket not withstanding).
But when it comes to manipulating URIs, or substituting their various parts, I feel the Fantom Uri is lacking somewhat.
And I find URI manipulation happens a lot. Even if just playing with files, there's often extension manipulation. (Even C# acknowledges this with a Path.GetFileNameWithoutExtension() method.)
The Problem
Example, if I have the URI:
uri := `path/name.ext?q=query#frag`
How do I create a new URI from uri that just substitutes name.ext with foo.bar but keeps the path, query, and frag? (I may be creating a redirection URL for example.)
I've used replace as a base word, but set, with, or swap could also work. Also, it'd be nice if null was accepted, that removed the appropriate section.
It feels as if Uri already started down this route with plusName and plusQuery but then the idea got lost somewhere...
brianWed 8 Jul 2015
Good write-up, but not sure the suggested solution really works - that is pretty complicated and ugly :) I think another tack might be to figure out how to make it work with getRange which does a nice job of splitting stuff up and keeping the leading scheme/host stuff and trailing query/frag stuff. Or maybe just just a constructor that works with the different parts such as:
Then you could manipulate all the parts and put it back together again pretty easy
SlimerDudeWed 8 Jul 2015
I think another missing method on Uri is Uri.isPathRel(). Uri already has:
Uri.isAbs()
Uri.isRel()
Uri.isPathAbs()
But no Uri.isPathRel()!
It is not my intention to flood the API with a plethora of useless methods, but given how Uri is a much used core literal, I the ones mentioned would be really handy.
Not as succinct as the single method I was hoping for, but I can apply the same code / pattern to all my use cases. (And probably create / replace my Uri wrapper class.)
So how about Uri.nameWithoutExt()? Other languages have mechanisms to acheive the same:
SlimerDude Wed 8 Jul 2015
RFC 3986 sec.3 (also known as Uniform Resource Identifier (URI): Generic Syntax) defines a URI as:
And Fantom's
Uri
class does an excellent job of breaking down a URI string into it's constituent parts. It also does a darn good job of encoding / decoding the different syntax parts too (this ticket not withstanding).But when it comes to manipulating URIs, or substituting their various parts, I feel the Fantom Uri is lacking somewhat.
And I find URI manipulation happens a lot. Even if just playing with files, there's often extension manipulation. (Even C# acknowledges this with a
Path.GetFileNameWithoutExtension()
method.)The Problem
Example, if I have the URI:
How do I create a new URI from
uri
that just substitutesname.ext
withfoo.bar
but keeps the path, query, and frag? (I may be creating a redirection URL for example.)Or how do I swap out just the query, or just the frag, or just the extension? How do I get the name without the extension?
Trials and Errors
Lets try walking through the first question and substitute
name.ext
forfoo.bar
:No query, no frag. How about using the optimised
plusName()
?Still no query and no frag. Okay, so lets add back the query and frag:
It's long and messy but the result looks better. But I thought frags went at the end of URIs? Lets double check:
D'Oh! That's not right! Lets re-work the expression:
Bingo! Phew, that was easy! Now... how do I swap out the
ext
...?While it's all possible, it is also hard work and the path to success is wrought with subtle errors.
The Idea
It'd be great if
Uri
had a couple of methods that returned a newUri
with the implied changes, such as:I've used
replace
as a base word, butset
,with
, orswap
could also work. Also, it'd be nice ifnull
was accepted, that removed the appropriate section.It feels as if
Uri
already started down this route withplusName
andplusQuery
but then the idea got lost somewhere...brian Wed 8 Jul 2015
Good write-up, but not sure the suggested solution really works - that is pretty complicated and ugly :) I think another tack might be to figure out how to make it work with getRange which does a nice job of splitting stuff up and keeping the leading scheme/host stuff and trailing query/frag stuff. Or maybe just just a constructor that works with the different parts such as:
Then you could manipulate all the parts and put it back together again pretty easy
SlimerDude Wed 8 Jul 2015
I think another missing method on Uri is
Uri.isPathRel()
.Uri
already has:Uri.isAbs()
Uri.isRel()
Uri.isPathAbs()
But no
Uri.isPathRel()
!It is not my intention to flood the API with a plethora of useless methods, but given how
Uri
is a much used core literal, I the ones mentioned would be really handy.SlimerDude Thu 9 Jul 2015
Good call, I'm liking the ctor:
Not as succinct as the single method I was hoping for, but I can apply the same code / pattern to all my use cases. (And probably create / replace my Uri wrapper class.)
So how about
Uri.nameWithoutExt()
? Other languages have mechanisms to acheive the same:(Not so keen on the
basename
method myself.)brian Fri 10 Jul 2015
I'm just going to tack this on to the existing 2357 ticket
Also note there is already a
sys::File.basename
methodSlimerDude Sun 12 Jul 2015
Wow - can't believe I missed that
basename
method!