A batteries included HTTP/1.1 client in OCaml

Fix path parsing bug in custom Uri module

The path_of_encoded function was incorrectly ordering "/" separators
in the accumulator. When building the path list in reverse and then
reversing it, "/" separators ended up at the wrong positions.

For example, "/status/200" was being parsed as ["/"; "/"; "status"; "200"]
instead of the correct ["/"; "status"; "/"; "200"]. This caused URLs
like http://localhost:8088/status/200 to be serialized incorrectly as
http://localhost:8088//status200, resulting in 404 errors.

The fix changes the order of prepending to the accumulator so that
"/" appears AFTER the segment when the list is reversed.

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>

+7 -2
+7 -2
lib/uri.ml
··· 385 385 let compare = compare_list String.compare 386 386 387 387 let path_of_encoded ps = 388 - (* Split on '/' keeping empty strings *) 388 + (* Split on '/' keeping empty strings. 389 + The path is represented as a list of tokens where "/" is a separator. 390 + For "/status/200", we want: ["/"; "status"; "/"; "200"] 391 + For "status/200", we want: ["status"; "/"; "200"] *) 389 392 let rec split acc i = 390 393 match String.index_from_opt ps i '/' with 391 394 | None -> ··· 393 396 List.rev (pct_decode last :: acc) 394 397 | Some j -> 395 398 let seg = String.sub ps i (j - i) in 396 - split (pct_decode seg :: "/" :: acc) (j + 1) 399 + (* Add "/" BEFORE seg in acc so it appears AFTER seg when reversed *) 400 + split ("/" :: pct_decode seg :: acc) (j + 1) 397 401 in 398 402 if ps = "" then [] 399 403 else if String.length ps > 0 && ps.[0] = '/' then 404 + (* Leading slash - add "/" and start parsing from index 1 *) 400 405 "/" :: (split [] 1) 401 406 else 402 407 split [] 0