Seems you have found a bug in suricata!
For example:
rule detecting ".." does not fire on ".." in http_uri:
alert http any any -> any any (msg:"ping"; content:"|2e 2e|"; http_uri; sid:100;)
T 192.168.4.6:34160 -> 45.33.32.156:80 [AP] #1735
GET /.. HTTP/1.1..Accept-Encoding: identity..Host: scanme.nmap.org..User-Agent: Python-urllib/3.6..Connec
tion: close....
T 192.168.4.6:45892 -> 93.184.216.34:80 [AP] #750
GET /.. HTTP/1.1..Accept-Encoding: identity..Host: example.com..User-Agent: Python-urllib/3.6..Connection
: close....
yet rule using http_raw_uri does fire:
alert http any any -> any any (msg:"ping"; content:"|2e 2e|"; http_raw_uri; sid:101;)
03/19/2019-16:19:48.570661 [**] [1:101:0] ping [**] [Classification: (null)] [Priority: 3] {TCP} 192.168.4.6:45932 -> 93.184.216.34:80
03/19/2019-16:19:57.027510 [**] [1:101:0] ping [**] [Classification: (null)] [Priority: 3] {TCP} 192.168.4.6:34160 -> 45.33.32.156:80
works as expected in snort:
alert tcp any any -> any $HTTP_PORTS (msg:"ping"; content:"|2e 2e|"; http_uri; sid:100;)
03/19-16:19:49.080887 [**] [1:100:0] ping [**] [Priority: 0] {TCP} 192.168.4.6:45936 -> 93.184.216.34:80
03/19-16:19:56.870987 [**] [1:100:0] ping [**] [Priority: 0] {TCP} 192.168.4.6:34160 -> 45.33.32.156:80
and strangely rule detecting ".." does fire on "...":
alert http any any -> any any (msg:"ping"; content:"|2e 2e|"; http_uri; sid:100;)
03/19/2019-16:08:14.678962 [**] [1:100:0] ping [**] [Classification: (null)] [Priority: 3] {TCP} 192.168.4.6:60804 -> 45.33.32.156:80
03/19/2019-16:08:15.860135 [**] [1:100:0] ping [**] [Classification: (null)] [Priority: 3] {TCP} 192.168.4.6:60810 -> 45.33.32.156:80
T 192.168.4.6:60804 -> 45.33.32.156:80 [AP] #29
GET /... HTTP/1.1..Host: scanme.nmap.org..User-Agent: curl/7.58.0..Accept: */*....
T 192.168.4.6:60810 -> 45.33.32.156:80 [AP] #35
GET /... HTTP/1.1..Host: scanme.nmap.org..User-Agent: curl/7.58.0..Accept: */*....