diff options
author | Adam Chlipala <adamc@hcoop.net> | 2009-09-12 09:31:50 -0400 |
---|---|---|
committer | Adam Chlipala <adamc@hcoop.net> | 2009-09-12 09:31:50 -0400 |
commit | 1273fb96a25f6f0521b27d97ccb92d0d82668f0f (patch) | |
tree | 3bd9d7c2e18155700eee1879cdc36505ce3431d1 | |
parent | f8f8014ff5b8f7edb115f88c3ae8e29757ac5f93 (diff) |
Change string URLification to avoid using the empty string, which confuses Apache no2slash()
-rw-r--r-- | lib/js/urweb.js | 7 | ||||
-rw-r--r-- | src/c/urweb.c | 27 | ||||
-rw-r--r-- | src/mono_opt.sml | 18 |
3 files changed, 43 insertions, 9 deletions
diff --git a/lib/js/urweb.js b/lib/js/urweb.js index 251f64ba..7349d2bf 100644 --- a/lib/js/urweb.js +++ b/lib/js/urweb.js @@ -464,10 +464,15 @@ function pflo(s) { } function uf(s) { - return escape(s).replace(new RegExp ("/", "g"), "%2F").replace(new RegExp ("\\+", "g"), "%2B"); + if (s.length == 0) + return "_"; + return (s[0] == '_' ? "_" : "") + + escape(s).replace(new RegExp ("/", "g"), "%2F").replace(new RegExp ("\\+", "g"), "%2B"); } function uu(s) { + if (s.length > 0 && s[0] == '_') + s = s.substring(1); return unescape(s.replace(new RegExp ("\\+", "g"), " ")); } diff --git a/src/c/urweb.c b/src/c/urweb.c index 774c5797..d5005af2 100644 --- a/src/c/urweb.c +++ b/src/c/urweb.c @@ -1479,9 +1479,16 @@ char *uw_Basis_urlifyFloat(uw_context ctx, uw_Basis_float n) { char *uw_Basis_urlifyString(uw_context ctx, uw_Basis_string s) { char *r, *p; - uw_check_heap(ctx, strlen(s) * 3 + 1); + if (s[0] == '\0') + return "_"; - for (r = p = ctx->heap.front; *s; s++) { + uw_check_heap(ctx, strlen(s) * 3 + 1 + !!(s[0] == '_')); + + r = p = ctx->heap.front; + if (s[0] == '_') + *p++ = '_'; + + for (; *s; s++) { char c = *s; if (c == ' ') @@ -1547,7 +1554,16 @@ uw_Basis_string uw_Basis_urlifyTime(uw_context ctx, uw_Basis_time t) { } uw_unit uw_Basis_urlifyString_w(uw_context ctx, uw_Basis_string s) { - uw_check(ctx, strlen(s) * 3); + if (s[0] == '\0') { + uw_check(ctx, 1); + uw_writec_unsafe(ctx, '_'); + return uw_unit_v; + } + + uw_check(ctx, strlen(s) * 3 + !!(s[0] == '_')); + + if (s[0] == '_') + uw_writec_unsafe(ctx, '_'); for (; *s; s++) { char c = *s; @@ -1612,6 +1628,11 @@ static uw_Basis_string uw_unurlifyString_to(uw_context ctx, char *r, char *s) { char *s1, *s2; int n; + if (*s2 == '_') + ++s2; + else if (s2[0] == '%' && s2[1] == '5' && (s2[2] == 'f' || s2[2] == 'F')) + s2 += 3; + for (s1 = r, s2 = s; *s2; ++s1, ++s2) { char c = *s2; diff --git a/src/mono_opt.sml b/src/mono_opt.sml index bf39b311..dd04a838 100644 --- a/src/mono_opt.sml +++ b/src/mono_opt.sml @@ -76,11 +76,19 @@ fun hexIt ch = | _ => s end -val urlifyString = String.translate (fn #" " => "+" - | ch => if Char.isAlphaNum ch then - str ch - else - "%" ^ hexIt ch) +fun urlifyString s = + case s of + "" => "_" + | _ => + (if String.sub (s, 0) = #"_" then + "_" + else + "") + ^ String.translate (fn #" " => "+" + | ch => if Char.isAlphaNum ch then + str ch + else + "%" ^ hexIt ch) s fun sqlifyInt n = #p_cast (Settings.currentDbms ()) (attrifyInt n, Settings.Int) |