Ruby's URI strips slashes when there's no host
Some URI schemes (the protocol portion of an address) don't require a hostname or network portion. For example
file:///home/rmg/scratchpad
According to the RFC, you can skip the //
if there's no host.
file:/home/rmg/scratchpad
Unfortunately, not everyone knows this, and therefore not every piece of software handles this!
The constant-named URI()
method in Ruby's URI lib likes to strip the //
for you. How helpful!
As I've discovered, Subversion is one of those pieces of software that doesn't handle this.
I took a look at the source code and found a way to fake things without resorting to monkey patching URI
and without re-writing large portions of the functionality.
uri = URI('file:///foo/bar/baz')
uri.to_s #=> 'file:/foo/bar/baz'
uri.send(:set_host, '')
uri.to_s #=> 'file:///foo/bar/baz'
It does require using #send
to invoke a protected method, though. Works for now, though, and I was able to wrap it up in a single well-tested method that does what I need so that I can at least refactor it later if it becomes a problem with newer versions.
require 'uri'
require 'pathname'
def clean_url(*parts)
uri = URI(parts.join('/'))
uri.path = Pathname(uri.path).cleanpath.to_s
uri.send(:set_host, '') unless uri.host
uri.to_s
end