URL特殊文字のエスケープ

どう書く?org (URL特殊文字のエスケープ)を動かしてみる。


module Main (main) where

import Network.URI
import Codec.Binary.UTF8.String (encodeString,decodeString )
import qualified System.IO.UTF8 as U

-- Haskell String を UTF-8 フォーマットのリストへ。
-- そしてURL特殊文字エスケープ
escape p = escapeURIString p . encodeString

-- URL特殊文字アンエスケープ
-- UTF-8 フォーマットのリストからHaskell Stringへ。
unescape = decodeString . unEscapeString

sample0 = "~url quote/ほげ"
sample1 = "!(foo*)"

escList = [ escape p x | p <- [isUnreserved,isAllowedInURI,isUnescapedInURI],
x <- [sample0, sample1]]
main = do
mapM_ U.putStrLn escList
mapM_ U.putStrLn $ map unescape escList

$ ghc --make esc.hs
[1 of 1] Compiling Main ( esc.hs, esc.o )
Linking esc ...
$ ./esc
~url%20quote%2F%E3%81%BB%E3%81%92
%21%28foo%2A%29
~url%20quote/%E3%81%BB%E3%81%92
!(foo*)
~url%20quote/%E3%81%BB%E3%81%92
!(foo*)
~url quote/ほげ
!(foo*)
~url quote/ほげ
!(foo*)
~url quote/ほげ
!(foo*)

●encodeString は Haskellの文字列からUTF8の文字列へ変更する。


Prelude> :m + Codec.Binary.UTF8.String
Prelude Codec.Binary.UTF8.String> let enc = encodeString "~url quote/ほげ"
Prelude Codec.Binary.UTF8.String> enc
"~url quote/\227\129\187\227\129\146"

「ほ」「げ」がそれぞれ3バイトの文字列になっている。


Prelude Codec.Binary.UTF8.String> :m + Network.URI
Prelude Codec.Binary.UTF8.String Network.URI> escapeURIString isAllowedInURI enc
"~url%20quote/%E3%81%BB%E3%81%92"

パーセント文字列へ。


$ echo "ほげ"|nkf -w|hd
00000000 e3 81 bb e3 81 92 0a |.......|