This is an automated email from the ASF dual-hosted git repository.

bneradt pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/trafficserver.git


The following commit(s) were added to refs/heads/master by this push:
     new 4c5fd62302 esi_nested_include test updates (#12471)
4c5fd62302 is described below

commit 4c5fd62302c0db681228169b2a267a36236fac03
Author: Brian Neradt <[email protected]>
AuthorDate: Wed Aug 27 20:06:10 2025 -0500

    esi_nested_include test updates (#12471)
    
    Some updates to the esi_nested_include autest. This uses Proxy Verifier
    and adds type hints.
---
 .../pluginTest/esi/esi_nested_include.replay.yaml  |  77 ++++++++++++
 .../pluginTest/esi/esi_nested_include.test.py      | 130 ++++++++-------------
 2 files changed, 126 insertions(+), 81 deletions(-)

diff --git a/tests/gold_tests/pluginTest/esi/esi_nested_include.replay.yaml 
b/tests/gold_tests/pluginTest/esi/esi_nested_include.replay.yaml
new file mode 100644
index 0000000000..e664aea62f
--- /dev/null
+++ b/tests/gold_tests/pluginTest/esi/esi_nested_include.replay.yaml
@@ -0,0 +1,77 @@
+#  Licensed to the Apache Software Foundation (ASF) under one
+#  or more contributor license agreements.  See the NOTICE file
+#  distributed with this work for additional information
+#  regarding copyright ownership.  The ASF licenses this file
+#  to you under the Apache License, Version 2.0 (the
+#  "License"); you may not use this file except in compliance
+#  with the License.  You may obtain a copy of the License at
+#
+#      http://www.apache.org/licenses/LICENSE-2.0
+#
+#  Unless required by applicable law or agreed to in writing, software
+#  distributed under the License is distributed on an "AS IS" BASIS,
+#  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+#  See the License for the specific language governing permissions and
+#  limitations under the License.
+
+sessions:
+
+- transactions:
+
+  # Initial request for the main ESI document
+  - client-request:
+      method: GET
+      url: /main.php
+      version: '1.1'
+      headers:
+        fields:
+        - [ Host, www.example.com ]
+        - [ Accept, "*/*" ]
+
+    server-response:
+      status: 200
+      headers:
+        fields:
+        - [ X-Esi, "1" ]
+        - [ Cache-Control, "private" ]
+        - [ Content-Type, "text/html" ]
+        - [ Connection, "close" ]
+        - [ Transfer-Encoding, "chunked" ]
+      content:
+        encoding: plain
+        data: "<head>\n<title>Main ESI 
Document</title>\n</head>\n<body>\n<esi:include 
src=\"http://www.example.com/esi-nested-include.html\"/>\n</body>\n"
+
+    # This is what the client receives /after/ ESI processing and fetching.
+    # Note: since the maximum inclusion depth is reached, the ESI include is
+    # not expanded.
+    proxy-response:
+      status: 200
+      headers:
+        fields:
+        - [ Content-Type, { value: "text/html", as: equal } ]
+      content:
+        encoding: plain
+        data: "<esi:include 
src=\"http://www.example.com/esi-nested-include.html\"/>"
+        verify: { as: contains }
+
+  # ESI nested include requests for the ATS-generated ESI include.
+  - client-request:
+      method: GET
+      url: /esi-nested-include.html
+      version: '1.1'
+      headers:
+        fields:
+        - [ Host, www.example.com ]
+
+    server-response:
+      status: 200
+      headers:
+        fields:
+        - [ X-Esi, "1" ]
+        - [ Cache-Control, "private" ]
+        - [ Content-Type, "text/html" ]
+        - [ Connection, "close" ]
+        - [ Transfer-Encoding, "chunked" ]
+      content:
+        encoding: plain
+        data: "<esi:include 
src=\"http://www.example.com/esi-nested-include.html\"/>"
diff --git a/tests/gold_tests/pluginTest/esi/esi_nested_include.test.py 
b/tests/gold_tests/pluginTest/esi/esi_nested_include.test.py
index d9ea49442d..b69c381415 100644
--- a/tests/gold_tests/pluginTest/esi/esi_nested_include.test.py
+++ b/tests/gold_tests/pluginTest/esi/esi_nested_include.test.py
@@ -17,8 +17,6 @@ Test nested include for the ESI plugin.
 #  See the License for the specific language governing permissions and
 #  limitations under the License.
 
-import os
-
 Test.Summary = '''
 Test nested include for the ESI plugin.
 '''
@@ -31,107 +29,77 @@ class EsiTest():
     A class that encapsulates the configuration and execution of a set of ESI
     test cases.
     """
-    """ static: The same server Process is used across all tests. """
-    _server = None
-    """ static: A counter to keep the ATS process names unique across tests. 
"""
-    _ts_counter = 0
-    """ static: A counter to keep any output file names unique across tests. 
"""
-    _output_counter = 0
-    """ The ATS process for this set of test cases. """
-    _ts = None
-
-    def __init__(self, plugin_config):
-        """
-        Args:
-            plugin_config (str): The config line to place in plugin.config for
-                the ATS process.
-        """
-        if EsiTest._server is None:
-            EsiTest._server = EsiTest._create_server()
 
-        self._ts = EsiTest._create_ats(self, plugin_config)
+    _replay_file: str = "esi_nested_include.replay.yaml"
 
-    @staticmethod
-    def _create_server():
+    def __init__(self, plugin_config) -> None:
         """
-        Create and start a server process.
+        :param plugin_config: esi.so configuration for plugin.config.
         """
-        # Configure our server.
-        server = Test.MakeOriginServer("server", lookup_key="{%uuid}")
-
-        # Generate the set of ESI responses.
-        request_header = {
-            "headers": "GET /esi-nested-include.php HTTP/1.1\r\n" + "Host: 
www.example.com\r\n" + "Content-Length: 0\r\n\r\n",
-            "timestamp": "1469733493.993",
-            "body": ""
-        }
-        esi_body = r'''<p>
-<esi:include src="http://www.example.com/esi-nested-include.html"/>
-</p>
-'''
-        response_header = {
-            "headers":
-                "HTTP/1.1 200 OK\r\n" + "X-Esi: 1\r\n" + "Cache-Control: 
private\r\n" + "Content-Type: text/html\r\n" +
-                "Connection: close\r\n" + "Content-Length: 
{}\r\n".format(len(esi_body)) + "\r\n",
-            "timestamp": "1469733493.993",
-            "body": esi_body
-        }
-        server.addResponse("sessionfile.log", request_header, response_header)
-
-        # Create a run to start the server.
-        tr = Test.AddTestRun("Start the server.")
-        tr.Processes.Default.StartBefore(server)
-        tr.Processes.Default.Command = "echo starting the server"
-        tr.Processes.Default.ReturnCode = 0
-        tr.StillRunningAfter = server
+        tr = Test.AddTestRun("Request the ESI generated document")
+        self._create_server(tr)
+        self._create_ats(tr, plugin_config)
+        self._create_client(tr)
+
+    def _create_server(self, tr: 'TestRun') -> 'Process':
+        """ Create and start a server process.
+        :param tr: The test run to add the server to.
+        :return: The server process.
+        """
+        # Configure our server using proxy verifier.
+        server = tr.AddVerifierServerProcess("server", self._replay_file, 
other_args='--format "{url}"')
+        self._server = server
+
+        # Validate server traffic
+        server.Streams.All += Testers.ContainsExpression('GET /main.php', 
'Verify the server received the initial request.')
+        server.Streams.All += Testers.ContainsExpression(
+            'GET /esi-nested-include.html', 'Verify the server received the 
nested include request.')
 
         return server
 
-    @staticmethod
-    def _create_ats(self, plugin_config):
-        """
-        Create and start an ATS process.
+    def _create_ats(self, tr: 'TestRun', plugin_config: str) -> 'Process':
+        """ Create and start an ATS process.
+        :param tr: The test run to add the ATS to.
+        :param plugin_config: The plugin configuration to use.
+        :return: The ATS process.
         """
-        EsiTest._ts_counter += 1
-
         # Configure ATS with a vanilla ESI plugin configuration.
-        ts = Test.MakeATSProcess("ts{}".format(EsiTest._ts_counter))
+        ts = tr.MakeATSProcess(f"ts")
+        self._ts = ts
         ts.Disk.records_config.update({
             'proxy.config.diags.debug.enabled': 1,
             'proxy.config.diags.debug.tags': 'http|plugin_esi',
         })
-        ts.Disk.remap_config.AddLine(f'map http://www.example.com/ 
http://127.0.0.1:{EsiTest._server.Variables.Port}')
+        server_port = self._server.Variables.http_port
+        ts.Disk.remap_config.AddLine(f'map http://www.example.com/ 
http://127.0.0.1:{server_port}')
         ts.Disk.plugin_config.AddLine(plugin_config)
 
         ts.Disk.diags_log.Content = Testers.ContainsExpression(
             r'The current esi inclusion depth \(3\) is larger than or equal to 
the max \(3\)',
             'Verify the ESI error concerning the max inclusion depth')
-
-        # Create a run to start the ATS process.
-        tr = Test.AddTestRun("Start the ATS process.")
-        tr.Processes.Default.StartBefore(ts)
-        tr.Processes.Default.Command = "echo starting ATS"
-        tr.Processes.Default.ReturnCode = 0
-        tr.StillRunningAfter = ts
         return ts
 
-    def run_test(self):
-        # Test 1: Verify basic ESI functionality without processing internal 
txn.
-        tr = Test.AddTestRun("First request")
-        tr.MakeCurlCommand(
-            f'http://127.0.0.1:{self._ts.Variables.port}/main.php -H"Host: 
www.example.com" '
-            '-H"Accept: */*" --verbose',
-            ts=self._ts)
-        tr.Processes.Default.ReturnCode = 0
-        tr.Processes.Default.Streams.stdout = "gold/nested_include_body.gold"
-        tr.StillRunningAfter = self._server
-        tr.StillRunningAfter = self._ts
+    def _create_client(self, tr: 'TestRun') -> None:
+        """ Create and start a client process to generate the request.
+        :param tr: The test run to add the client to.
+        """
+        # Note, just request the main.php file. Otherwise the client will do 
the
+        # ESI requests in the replay file as well.
+        p = tr.AddVerifierClientProcess(
+            "client", self._replay_file, http_ports=[self._ts.Variables.port], 
other_args='--format "{url}" --keys /main.php')
+        p.ReturnCode = 0
+        p.StartBefore(self._server)
+        p.StartBefore(self._ts)
+
+        # Double check that the client received the response.
+        p.Streams.stdout += Testers.ContainsExpression(
+            'Received an HTTP/1 chunked body', 'Verify the client received the 
response.')
+
+        p.Streams.stdout += Testers.ContainsExpression(
+            'esi:include 
src="http://www.example.com/esi-nested-include.html"/>', 'Verify the ATS 
received the esi include.')
 
 
 #
 # Configure and run the test cases.
 #
-
-# Run the tests with ESI configured with private response.
-first_test = EsiTest(plugin_config='esi.so')
-first_test.run_test()
+EsiTest(plugin_config='esi.so')

Reply via email to