1'''
2Verify that request following a ill-formed request is not processed
3'''
4#  Licensed to the Apache Software Foundation (ASF) under one
5#  or more contributor license agreements.  See the NOTICE file
6#  distributed with this work for additional information
7#  regarding copyright ownership.  The ASF licenses this file
8#  to you under the Apache License, Version 2.0 (the
9#  "License"); you may not use this file except in compliance
10#  with the License.  You may obtain a copy of the License at
11#
12#      http://www.apache.org/licenses/LICENSE-2.0
13#
14#  Unless required by applicable law or agreed to in writing, software
15#  distributed under the License is distributed on an "AS IS" BASIS,
16#  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17#  See the License for the specific language governing permissions and
18#  limitations under the License.
19
20import os
21
22Test.Summary = '''
23Verify that request following a ill-formed request is not processed
24'''
25Test.ContinueOnFail = True
26ts = Test.MakeATSProcess("ts", enable_cache=True)
27
28ts.Disk.records_config.update({'proxy.config.diags.debug.tags': 'http',
29                               'proxy.config.diags.debug.enabled': 0,
30                               })
31
32Test.ContinueOnFail = True
33server = Test.MakeOriginServer("server")
34request_header = {"headers": "GET / HTTP/1.1\r\nHost: www.example.com\r\n\r\n", "timestamp": "1469733493.993", "body": ""}
35response_header = {
36    "headers": "HTTP/1.1 200 OK\r\nConnection: close\r\nLast-Modified: Tue, 08 May 2018 15:49:41 GMT\r\nCache-Control: max-age=1000\r\n\r\n",
37    "timestamp": "1469733493.993",
38    "body": "xxx"}
39server.addResponse("sessionlog.json", request_header, response_header)
40
41ts.Disk.remap_config.AddLine(
42    'map / http://127.0.0.1:{0}'.format(server.Variables.Port)
43)
44
45# Make a good request to get item in the cache for later tests
46tr = Test.AddTestRun("Good control")
47tr.Processes.Default.StartBefore(server)
48tr.Processes.Default.StartBefore(Test.Processes.ts)
49tr.Processes.Default.Command = 'printf "GET / HTTP/1.1\r\nHost: bob\r\n\r\n" | nc  127.0.0.1 {}'.format(ts.Variables.port)
50tr.Processes.Default.ReturnCode = 0
51
52tr = Test.AddTestRun("space after header name")
53tr.Processes.Default.Command = 'printf "GET / HTTP/1.1\r\nHost : bob\r\n\r\nGET / HTTP/1.1\r\nHost: boa\r\n\r\n" | nc  127.0.0.1 {}'.format(
54    ts.Variables.port)
55tr.Processes.Default.ReturnCode = 0
56tr.Processes.Default.Streams.stdout = 'gold/bad_good_request.gold'
57
58tr = Test.AddTestRun("Bad protocol number")
59tr.Processes.Default.Command = 'printf "GET / HTTP/11.1\r\nhost: bob\r\n\r\nGET / HTTP/1.1\r\nHost: boa\r\n\r\n" | nc  127.0.0.1 {}'.format(
60    ts.Variables.port)
61tr.Processes.Default.ReturnCode = 0
62tr.Processes.Default.Streams.stdout = 'gold/bad_protocol_number.gold'
63
64tr = Test.AddTestRun("Unsupported Transfer Encoding value")
65tr.Processes.Default.Command = 'printf "GET / HTTP/1.1\r\nhost: bob\r\ntransfer-encoding: random\r\n\r\nGET / HTTP/1.1\r\nHost: boa\r\n\r\n" | nc  127.0.0.1 {}'.format(
66    ts.Variables.port)
67tr.Processes.Default.ReturnCode = 0
68tr.Processes.Default.Streams.stdout = 'gold/bad_te_value.gold'
69
70# TRACE request with a body
71tr = Test.AddTestRun("Trace request with a body")
72tr.Processes.Default.Command = 'printf "TRACE /foo HTTP/1.1\r\nHost: bob\r\nContent-length:2\r\n\r\nokGET / HTTP/1.1\r\nHost: boa\r\n\r\n" | nc  127.0.0.1 {}'.format(
73    ts.Variables.port)
74tr.Processes.Default.ReturnCode = 0
75tr.Processes.Default.Streams.stdout = 'gold/bad_good_request.gold'
76
77tr = Test.AddTestRun("Trace request with a chunked body")
78tr.Processes.Default.Command = 'printf "TRACE /foo HTTP/1.1\r\nHost: bob\r\ntransfer-encoding: chunked\r\n\r\n2\r\nokGGET / HTTP/1.1\r\nHost: boa\r\n\r\n" | nc  127.0.0.1 {}'.format(
79    ts.Variables.port)
80tr.Processes.Default.ReturnCode = 0
81tr.Processes.Default.Streams.stdout = 'gold/bad_good_request.gold'
82
83tr = Test.AddTestRun("Trace request with a chunked body via curl")
84tr.Processes.Default.Command = 'curl -v --http1.1 --header "Transfer-Encoding: chunked" -d aaa -X TRACE -k http://127.0.0.1:{}/foo'.format(
85    ts.Variables.port)
86tr.Processes.Default.ReturnCode = 0
87tr.Processes.Default.Streams.All = 'gold/bad_good_request.gold'
88
89tr = Test.AddTestRun("Trace request via curl")
90tr.Processes.Default.Command = 'curl -v --http1.1 -X TRACE -k http://127.0.0.1:{}/bar'.format(ts.Variables.port)
91tr.Processes.Default.ReturnCode = 0
92tr.Processes.Default.Streams.All = Testers.ContainsExpression(
93    r"HTTP/1.1 501 Unsupported method \('TRACE'\)",
94    "microserver does not support TRACE")
95
96# Methods are case sensitive. Verify that "gET" is not confused with "GET".
97tr = Test.AddTestRun("mixed case method")
98tr.Processes.Default.Command = 'printf "gET / HTTP/1.1\r\nHost:bob\r\n\r\nGET / HTTP/1.1\r\nHost: boa\r\n\r\n" | nc  127.0.0.1 {}'.format(
99    ts.Variables.port)
100tr.Processes.Default.ReturnCode = 0
101tr.Processes.Default.Streams.stdout = 'gold/bad_method.gold'
102