tclurlencodeurldecode

Check for the existence of a file: URL that uses URLEncoding in Tcl 8.5.9


What is the simplest way to check for the existence of a file specified by a file: URL that uses URLEncoding in Tcl 8.5.9?

::http::geturl says it doesn't support file URLs.

file exists requires URLDecoding. There doesn't seem to be a builtin proc for URLDecoding. Have I missed it?

Are there any other builtin ways to do this? Do newer versions of Tcl provide more support for this?

If no builtin way, is there a recommended library for this? Either for directly handling file: URLs, or for URLDecoding?


Solution

  • In my projects, I tend to use a combination of a URI/URL processor (uri::split) plus a URL decoder (urlDecode) for postprocessing:

    Step 1: URL processing

    % package req uri
    1.2.7
    % set parsedURL [::uri::split file:///path/to/a%20file]
    path /path/to/a%20file scheme file
    

    Step 2: URL (percent-) decoding

    Source the following:

    proc urlDecode {str} {
        set specialMap {"[" "%5B" "]" "%5D"}
        set seqRE {%([0-9a-fA-F]{2})}
        set replacement {[format "%c" [scan "\1" "%2x"]]}
        set modStr [regsub -all $seqRE [string map $specialMap $str] $replacement]
        return [encoding convertfrom utf-8 [subst -nobackslash -novariable $modStr]]
    }
    

    Then:

    % set fp [urlDecode [dict get $parsedURL path]]
    /path/to/a file
    % file exists $fp
    % 0
    

    Depending on the portability and robustness aimed at, you might want to use file normalize & friends.