You are viewing a plain text version of this content. The canonical link for it is here.
Posted to github@trafficserver.apache.org by "traeak (via GitHub)" <gi...@apache.org> on 2026/10/06 15:23:16 UTC

[PR] Add proxy.config.http.parent_proxy.go_direct [trafficserver]

traeak opened a new pull request, #13801:
URL: https://github.com/apache/trafficserver/pull/13801

   Allow a transaction to skip parent.config, next-hop strategy, and plugin-chosen parent selection and connect straight to the remapped origin, e.g. per remap rule via conf_remap. It yields to no_dns_just_forward_to_parent, which leaves origin DNS to the parent.


-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@trafficserver.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org


Re: [PR] Add proxy.config.http.bypass_parent [trafficserver]

Posted by "traeak (via GitHub)" <gi...@apache.org>.
traeak commented on code in PR #13801:
URL: https://github.com/apache/trafficserver/pull/13801#discussion_r4232269736


##########
tests/gold_tests/parent_proxy/replays/bypass_parent_connect.replay.yaml:
##########
@@ -0,0 +1,78 @@
+#  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.
+
+#
+# CONNECT requests remapped to the verifier server. The connect-direct.test rule
+# sets proxy.config.http.bypass_parent, so ATS tunnels straight to the
+# server and the follow-up GET travels through the tunnel. The
+# connect-parent.test rule does not, so ATS sends the CONNECT to the dead parent
+# and returns a 502.
+#
+
+meta:
+  version: "1.0"
+
+sessions:
+- transactions:
+  - client-request:
+      method: CONNECT
+      version: "1.1"
+      url: connect-direct.test:80
+      headers:
+        fields:
+        - [ Host, connect-direct.test:80 ]
+        - [ uuid, connect-direct ]
+    # The CONNECT itself never reaches the server; ATS answers it once the
+    # tunnel is open.
+    server-response:
+      status: 200

Review Comment:
   minor nit.



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@trafficserver.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org


Re: [PR] Add proxy.config.http.bypass_parent [trafficserver]

Posted by "traeak (via GitHub)" <gi...@apache.org>.
traeak merged PR #13801:
URL: https://github.com/apache/trafficserver/pull/13801


-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@trafficserver.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org


Re: [PR] Add proxy.config.http.bypass_parent [trafficserver]

Posted by "traeak (via GitHub)" <gi...@apache.org>.
traeak commented on code in PR #13801:
URL: https://github.com/apache/trafficserver/pull/13801#discussion_r4232540371


##########
tests/gold_tests/parent_proxy/plugins/parent_override_test.cc:
##########
@@ -0,0 +1,110 @@
+/** @file
+
+  A test plugin that routes a transaction to a plugin-chosen parent.
+
+  The X-Parent-Override request header selects the API:
+    proxy-set       - TSHttpTxnParentProxySet()
+    response-action - TSHttpTxnResponseActionSet()
+
+  Either way the parent is 127.0.0.1:1, where nothing listens, so a request
+  routed to it fails with a 502.
+
+  @section license License
+
+  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.
+ */
+
+#include <ts/ts.h>
+
+#include <string_view>
+
+namespace
+{
+constexpr char             PLUGIN_NAME[]   = "parent_override_test";
+constexpr char             DEAD_PARENT[]   = "127.0.0.1";
+constexpr int              DEAD_PORT       = 1;
+constexpr std::string_view OVERRIDE_HEADER = "X-Parent-Override";
+
+DbgCtl dbg_ctl{PLUGIN_NAME};
+
+std::string_view
+override_mode(TSHttpTxn txnp)
+{
+  TSMBuffer        bufp    = nullptr;
+  TSMLoc           hdr_loc = TS_NULL_MLOC;
+  std::string_view mode;
+
+  if (TSHttpTxnClientReqGet(txnp, &bufp, &hdr_loc) != TS_SUCCESS) {
+    return mode;
+  }
+
+  TSMLoc field_loc = TSMimeHdrFieldFind(bufp, hdr_loc, OVERRIDE_HEADER.data(), static_cast<int>(OVERRIDE_HEADER.size()));
+  if (field_loc != TS_NULL_MLOC) {
+    int         len   = 0;
+    char const *value = TSMimeHdrFieldValueStringGet(bufp, hdr_loc, field_loc, -1, &len);
+
+    if (value != nullptr) {
+      mode = {value, static_cast<size_t>(len)};
+    }
+    TSHandleMLocRelease(bufp, hdr_loc, field_loc);
+  }
+  TSHandleMLocRelease(bufp, TS_NULL_MLOC, hdr_loc);
+  return mode;

Review Comment:
   In practice this works as only the MLocs are allocated/deallocated.  The std::string_view points to valid memory inside the header.  Since it's not explicitly documented as part of the API I guess we can make this change.



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@trafficserver.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org


Re: [PR] Add proxy.config.http.bypass_parent [trafficserver]

Posted by "traeak (via GitHub)" <gi...@apache.org>.
traeak commented on code in PR #13801:
URL: https://github.com/apache/trafficserver/pull/13801#discussion_r4232904677


##########
tests/gold_tests/parent_proxy/replays/bypass_parent_cache.replay.yaml:
##########
@@ -0,0 +1,191 @@
+#  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.
+
+#
+# proxy.config.http.bypass_parent with the cache enabled, where
+# uncacheable_requests_bypass_parent does not apply. The parent is dead with
+# go_direct=false, so a request routed to it fails with a 502. With the
+# override, a cache miss goes straight to the origin and is cached, a repeat is
+# served from cache, and a stale object is revalidated directly with the origin.
+#
+
+meta:
+  version: "1.0"
+
+autest:
+  description: 'bypass_parent bypasses parent.config on cache misses and revalidations'
+
+  dns:
+    name: 'dns-bypass-parent-cache'
+
+  server:
+    name: 'server-bypass-parent-cache'
+
+  client:
+    name: 'client-bypass-parent-cache'
+
+  ats:
+    name: 'ts-bypass-parent-cache'
+    process_config:
+      enable_cache: true
+
+    records_config:
+      proxy.config.diags.debug.enabled: 1
+      proxy.config.diags.debug.tags: 'http_trans|parent_select'
+      proxy.config.http.parent_proxy.self_detect: 0
+      proxy.config.http.parent_proxy.total_connect_attempts: 1
+      proxy.config.http.parent_proxy.per_parent_connect_attempts: 1
+
+    parent_config:
+      - 'dest_domain=. parent="127.0.0.1:1|1" go_direct=false parent_is_proxy=true'
+
+    remap_config:
+      - from: 'http://parent.test/'
+        to: 'http://origin.test:{SERVER_HTTP_PORT}/'
+      - from: 'http://direct.test/'
+        to: 'http://origin.test:{SERVER_HTTP_PORT}/'
+        plugins:
+          - name: 'conf_remap.so'
+            args:
+              - 'proxy.config.http.bypass_parent=1'
+
+    log_validation:
+      traffic_out:
+        contains:
+          - expression: 'bypassing parent selection due to proxy\.config\.http\.bypass_parent'
+            description: 'Parent selection is bypassed for the bypass_parent rule'
+
+sessions:
+- transactions:
+  # A cacheable miss without the override: the dead parent is selected.
+  - all: { headers: { fields: [[ uuid, parent-miss ]]}}
+    client-request:
+      method: GET
+      version: "1.1"
+      url: /parent-miss
+      headers:
+        fields:
+        - [ Host, parent.test ]
+        - [ Content-Length, "0" ]
+    server-response:
+      status: 200
+      reason: OK
+      headers:
+        fields:
+        - [ Content-Length, "0" ]
+        - [ Cache-Control, max-age=300 ]
+    proxy-response:
+      status: 502
+
+  # A cache miss with the override: the origin is reached directly.
+  - all: { headers: { fields: [[ uuid, direct-miss ]]}}
+    client-request:
+      method: GET
+      version: "1.1"
+      url: /cached
+      headers:
+        fields:
+        - [ Host, direct.test ]
+        - [ Content-Length, "0" ]
+    proxy-request:
+      url:
+      - [ path, { value: /cached, as: equal } ]
+    server-response:
+      status: 200
+      reason: OK
+      headers:
+        fields:
+        - [ Content-Length, "4" ]
+        - [ Cache-Control, max-age=300 ]
+        - [ X-Response, origin ]
+    proxy-response:
+      status: 200
+      headers:
+        fields:
+        - [ X-Response, { value: origin, as: equal } ]
+
+  # A repeat of the same GET is a fresh hit served from cache.
+  - all: { headers: { fields: [[ uuid, direct-hit ]]}}
+    client-request:
+      method: GET
+      version: "1.1"
+      url: /cached
+      headers:
+        fields:
+        - [ Host, direct.test ]
+        - [ Content-Length, "0" ]
+      delay: 100ms
+    server-response:
+      status: 500
+      reason: Internal Server Error
+      headers:
+        fields:
+        - [ Content-Length, "0" ]
+        - [ X-Response, should-not-be-used ]
+    proxy-response:
+      status: 200
+      headers:
+        fields:
+        - [ X-Response, { value: origin, as: equal } ]
+
+  # Populate the cache with an object that will go stale.
+  - all: { headers: { fields: [[ uuid, direct-stale-fill ]]}}
+    client-request:
+      method: GET
+      version: "1.1"
+      url: /stale
+      headers:
+        fields:
+        - [ Host, direct.test ]
+        - [ Content-Length, "0" ]
+    server-response:
+      status: 200
+      reason: OK
+      headers:
+        fields:
+        - [ Content-Length, "4" ]
+        - [ Cache-Control, max-age=1 ]
+        - [ Last-Modified, "Thu, 01 Jan 2026 00:00:00 GMT" ]

Review Comment:
   turn back the clock, more than this breaks.



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@trafficserver.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org


Re: [PR] Add proxy.config.http.bypass_parent [trafficserver]

Posted by "Copilot (via GitHub)" <gi...@apache.org>.
Copilot commented on code in PR #13801:
URL: https://github.com/apache/trafficserver/pull/13801#discussion_r4230988455


##########
doc/admin-guide/plugins/lua.en.rst:
##########
@@ -4821,6 +4821,7 @@ Http config constants
     TS_LUA_CONFIG_WEBSOCKET_NO_ACTIVITY_TIMEOUT
     TS_LUA_CONFIG_WEBSOCKET_ACTIVE_TIMEOUT
     TS_LUA_CONFIG_HTTP_UNCACHEABLE_REQUESTS_BYPASS_PARENT
+    TS_LUA_CONFIG_HTTP_BYPASS_PARENT

Review Comment:
   The docs add `TS_LUA_CONFIG_HTTP_BYPASS_PARENT`, but this PR doesn’t show the corresponding Lua plugin constant being added/exposed. If Lua constants are not auto-derived from `TSOverridableConfigKey`, this line will be inaccurate. Either add the Lua binding/constant in the Lua plugin implementation, or remove/adjust this doc entry to match the actual exported constants.



##########
tests/gold_tests/parent_proxy/replays/bypass_parent_connect.replay.yaml:
##########
@@ -0,0 +1,78 @@
+#  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.
+
+#
+# CONNECT requests remapped to the verifier server. The connect-direct.test rule
+# sets proxy.config.http.bypass_parent, so ATS tunnels straight to the
+# server and the follow-up GET travels through the tunnel. The
+# connect-parent.test rule does not, so ATS sends the CONNECT to the dead parent
+# and returns a 502.
+#
+
+meta:
+  version: "1.0"
+
+sessions:
+- transactions:
+  - client-request:
+      method: CONNECT
+      version: "1.1"
+      url: connect-direct.test:80
+      headers:
+        fields:
+        - [ Host, connect-direct.test:80 ]
+        - [ uuid, connect-direct ]
+    # The CONNECT itself never reaches the server; ATS answers it once the
+    # tunnel is open.
+    server-response:
+      status: 200

Review Comment:
   This transaction’s comment states that the CONNECT is not forwarded to the origin (ATS responds after the tunnel is established), but the replay still defines a `server-response` for the CONNECT. This is internally inconsistent and can make the verifier expect an origin HTTP request that should never occur. Recommend removing the `server-response` block for the CONNECT transactions (and rely on the follow-up tunneled GET to prove the tunnel is established), or adjust the test narrative/expectations so the origin is expected to receive CONNECT.



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@trafficserver.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org


Re: [PR] Add proxy.config.http.bypass_parent [trafficserver]

Posted by "Copilot (via GitHub)" <gi...@apache.org>.
Copilot commented on code in PR #13801:
URL: https://github.com/apache/trafficserver/pull/13801#discussion_r4232720449


##########
tests/gold_tests/parent_proxy/replays/bypass_parent_cache.replay.yaml:
##########
@@ -0,0 +1,191 @@
+#  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.
+
+#
+# proxy.config.http.bypass_parent with the cache enabled, where
+# uncacheable_requests_bypass_parent does not apply. The parent is dead with
+# go_direct=false, so a request routed to it fails with a 502. With the
+# override, a cache miss goes straight to the origin and is cached, a repeat is
+# served from cache, and a stale object is revalidated directly with the origin.
+#
+
+meta:
+  version: "1.0"
+
+autest:
+  description: 'bypass_parent bypasses parent.config on cache misses and revalidations'
+
+  dns:
+    name: 'dns-bypass-parent-cache'
+
+  server:
+    name: 'server-bypass-parent-cache'
+
+  client:
+    name: 'client-bypass-parent-cache'
+
+  ats:
+    name: 'ts-bypass-parent-cache'
+    process_config:
+      enable_cache: true
+
+    records_config:
+      proxy.config.diags.debug.enabled: 1
+      proxy.config.diags.debug.tags: 'http_trans|parent_select'
+      proxy.config.http.parent_proxy.self_detect: 0
+      proxy.config.http.parent_proxy.total_connect_attempts: 1
+      proxy.config.http.parent_proxy.per_parent_connect_attempts: 1
+
+    parent_config:
+      - 'dest_domain=. parent="127.0.0.1:1|1" go_direct=false parent_is_proxy=true'
+
+    remap_config:
+      - from: 'http://parent.test/'
+        to: 'http://origin.test:{SERVER_HTTP_PORT}/'
+      - from: 'http://direct.test/'
+        to: 'http://origin.test:{SERVER_HTTP_PORT}/'
+        plugins:
+          - name: 'conf_remap.so'
+            args:
+              - 'proxy.config.http.bypass_parent=1'
+
+    log_validation:
+      traffic_out:
+        contains:
+          - expression: 'bypassing parent selection due to proxy\.config\.http\.bypass_parent'
+            description: 'Parent selection is bypassed for the bypass_parent rule'
+
+sessions:
+- transactions:
+  # A cacheable miss without the override: the dead parent is selected.
+  - all: { headers: { fields: [[ uuid, parent-miss ]]}}
+    client-request:
+      method: GET
+      version: "1.1"
+      url: /parent-miss
+      headers:
+        fields:
+        - [ Host, parent.test ]
+        - [ Content-Length, "0" ]
+    server-response:
+      status: 200
+      reason: OK
+      headers:
+        fields:
+        - [ Content-Length, "0" ]
+        - [ Cache-Control, max-age=300 ]
+    proxy-response:
+      status: 502
+
+  # A cache miss with the override: the origin is reached directly.
+  - all: { headers: { fields: [[ uuid, direct-miss ]]}}
+    client-request:
+      method: GET
+      version: "1.1"
+      url: /cached
+      headers:
+        fields:
+        - [ Host, direct.test ]
+        - [ Content-Length, "0" ]
+    proxy-request:
+      url:
+      - [ path, { value: /cached, as: equal } ]
+    server-response:
+      status: 200
+      reason: OK
+      headers:
+        fields:
+        - [ Content-Length, "4" ]
+        - [ Cache-Control, max-age=300 ]
+        - [ X-Response, origin ]
+    proxy-response:
+      status: 200
+      headers:
+        fields:
+        - [ X-Response, { value: origin, as: equal } ]
+
+  # A repeat of the same GET is a fresh hit served from cache.
+  - all: { headers: { fields: [[ uuid, direct-hit ]]}}
+    client-request:
+      method: GET
+      version: "1.1"
+      url: /cached
+      headers:
+        fields:
+        - [ Host, direct.test ]
+        - [ Content-Length, "0" ]
+      delay: 100ms
+    server-response:
+      status: 500
+      reason: Internal Server Error
+      headers:
+        fields:
+        - [ Content-Length, "0" ]
+        - [ X-Response, should-not-be-used ]
+    proxy-response:
+      status: 200
+      headers:
+        fields:
+        - [ X-Response, { value: origin, as: equal } ]
+
+  # Populate the cache with an object that will go stale.
+  - all: { headers: { fields: [[ uuid, direct-stale-fill ]]}}
+    client-request:
+      method: GET
+      version: "1.1"
+      url: /stale
+      headers:
+        fields:
+        - [ Host, direct.test ]
+        - [ Content-Length, "0" ]
+    server-response:
+      status: 200
+      reason: OK
+      headers:
+        fields:
+        - [ Content-Length, "4" ]
+        - [ Cache-Control, max-age=1 ]
+        - [ Last-Modified, "Thu, 01 Jan 2026 00:00:00 GMT" ]

Review Comment:
   This test uses a fixed `Last-Modified` year value, which makes the replay time-dependent when run in environments where the current date could precede that timestamp (and makes it harder to reason about staleness semantics). Prefer using a clearly historical date (e.g., a year far in the past) or another staleness mechanism that doesn’t depend on wall-clock time, so the replay remains stable long-term.



##########
tests/gold_tests/parent_proxy/replays/bypass_parent_connect.replay.yaml:
##########
@@ -0,0 +1,78 @@
+#  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.
+
+#
+# CONNECT requests remapped to the verifier server. The connect-direct.test rule
+# sets proxy.config.http.bypass_parent, so ATS tunnels straight to the
+# server and the follow-up GET travels through the tunnel. The
+# connect-parent.test rule does not, so ATS sends the CONNECT to the dead parent
+# and returns a 502.
+#
+
+meta:
+  version: "1.0"
+
+sessions:
+- transactions:
+  - client-request:
+      method: CONNECT
+      version: "1.1"
+      url: connect-direct.test:80
+      headers:
+        fields:
+        - [ Host, connect-direct.test:80 ]
+        - [ uuid, connect-direct ]
+    # The CONNECT itself never reaches the server; ATS answers it once the
+    # tunnel is open.
+    server-response:
+      status: 200
+    proxy-response:
+      status: 200

Review Comment:
   The comment states the CONNECT never reaches the server, but the replay includes a `server-response` with an HTTP status for that CONNECT transaction. To avoid ambiguity for future maintainers, either remove the `server-response` for this CONNECT transaction (if it’s not actually expected to be emitted by the verifier server), or adjust the comment to explain why the replay still defines a server-response in this harness.



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@trafficserver.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org


Re: [PR] Add proxy.config.http.bypass_parent [trafficserver]

Posted by "Copilot (via GitHub)" <gi...@apache.org>.
Copilot commented on code in PR #13801:
URL: https://github.com/apache/trafficserver/pull/13801#discussion_r4232477447


##########
tests/gold_tests/parent_proxy/plugins/parent_override_test.cc:
##########
@@ -0,0 +1,110 @@
+/** @file
+
+  A test plugin that routes a transaction to a plugin-chosen parent.
+
+  The X-Parent-Override request header selects the API:
+    proxy-set       - TSHttpTxnParentProxySet()
+    response-action - TSHttpTxnResponseActionSet()
+
+  Either way the parent is 127.0.0.1:1, where nothing listens, so a request
+  routed to it fails with a 502.
+
+  @section license License
+
+  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.
+ */
+
+#include <ts/ts.h>
+
+#include <string_view>
+
+namespace
+{
+constexpr char             PLUGIN_NAME[]   = "parent_override_test";
+constexpr char             DEAD_PARENT[]   = "127.0.0.1";
+constexpr int              DEAD_PORT       = 1;
+constexpr std::string_view OVERRIDE_HEADER = "X-Parent-Override";
+
+DbgCtl dbg_ctl{PLUGIN_NAME};
+
+std::string_view
+override_mode(TSHttpTxn txnp)
+{
+  TSMBuffer        bufp    = nullptr;
+  TSMLoc           hdr_loc = TS_NULL_MLOC;
+  std::string_view mode;
+
+  if (TSHttpTxnClientReqGet(txnp, &bufp, &hdr_loc) != TS_SUCCESS) {
+    return mode;
+  }
+
+  TSMLoc field_loc = TSMimeHdrFieldFind(bufp, hdr_loc, OVERRIDE_HEADER.data(), static_cast<int>(OVERRIDE_HEADER.size()));
+  if (field_loc != TS_NULL_MLOC) {
+    int         len   = 0;
+    char const *value = TSMimeHdrFieldValueStringGet(bufp, hdr_loc, field_loc, -1, &len);
+
+    if (value != nullptr) {
+      mode = {value, static_cast<size_t>(len)};
+    }
+    TSHandleMLocRelease(bufp, hdr_loc, field_loc);
+  }
+  TSHandleMLocRelease(bufp, TS_NULL_MLOC, hdr_loc);
+  return mode;

Review Comment:
   override_mode() returns a std::string_view that aliases header-buffer memory, but it releases the header MLocs before returning. This makes the lifetime of the referenced memory unclear/fragile and risks use-after-free if the SDK invalidates pointers after handle release. Prefer returning a std::string (copy) or performing the mode comparison while the MLocs are still held (e.g., parse into an enum/bool before releasing).



##########
include/ts/apidefs.h.in:
##########
@@ -922,6 +922,7 @@ enum TSOverridableConfigKey {
   TS_CONFIG_HTTP_CACHE_MAX_STALE_AGE_PERCENT,
   TS_CONFIG_HTTP_PER_SERVER_CONNECTION_METRIC_ENABLED,
   TS_CONFIG_HTTP_PER_SERVER_CONNECTION_METRIC_AGGREGATE,
+  TS_CONFIG_HTTP_BYPASS_PARENT,
   TS_CONFIG_LAST_ENTRY,

Review Comment:
   This PR introduces a new public overridable-config key (TS_CONFIG_HTTP_BYPASS_PARENT). The added gold tests validate conf_remap-driven overrides, but they don’t exercise the C API path (TSHttpTxnConfigIntSet/TSHttpTxnConfigIntGet) using the new enum value. Adding a small autest plugin-driven case that sets TS_CONFIG_HTTP_BYPASS_PARENT via TSHttpTxnConfigIntSet would help ensure the enum-to-record mapping is wired correctly and prevent regressions in the public API.



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@trafficserver.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org


Re: [PR] Add proxy.config.http.bypass_parent [trafficserver]

Posted by "traeak (via GitHub)" <gi...@apache.org>.
traeak commented on code in PR #13801:
URL: https://github.com/apache/trafficserver/pull/13801#discussion_r4232909658


##########
tests/gold_tests/parent_proxy/replays/bypass_parent_connect.replay.yaml:
##########
@@ -0,0 +1,78 @@
+#  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.
+
+#
+# CONNECT requests remapped to the verifier server. The connect-direct.test rule
+# sets proxy.config.http.bypass_parent, so ATS tunnels straight to the
+# server and the follow-up GET travels through the tunnel. The
+# connect-parent.test rule does not, so ATS sends the CONNECT to the dead parent
+# and returns a 502.
+#
+
+meta:
+  version: "1.0"
+
+sessions:
+- transactions:
+  - client-request:
+      method: CONNECT
+      version: "1.1"
+      url: connect-direct.test:80
+      headers:
+        fields:
+        - [ Host, connect-direct.test:80 ]
+        - [ uuid, connect-direct ]
+    # The CONNECT itself never reaches the server; ATS answers it once the
+    # tunnel is open.
+    server-response:
+      status: 200
+    proxy-response:
+      status: 200

Review Comment:
   won't bother.



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@trafficserver.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org


Re: [PR] Add proxy.config.http.bypass_parent [trafficserver]

Posted by "Copilot (via GitHub)" <gi...@apache.org>.
Copilot commented on code in PR #13801:
URL: https://github.com/apache/trafficserver/pull/13801#discussion_r4230447707


##########
tests/gold_tests/parent_proxy/bypass_parent.test.py:
##########
@@ -0,0 +1,80 @@
+'''
+Verify proxy.config.http.bypass_parent bypasses parent selection.
+'''
+#  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.
+
+Test.Summary = '''
+Verify proxy.config.http.bypass_parent bypasses parent.config, next-hop
+strategies, plugin-set parents, and CONNECT parenting, and yields to
+no_dns_just_forward_to_parent.
+'''
+
+Test.ATSReplayTest(replay_file='replays/bypass_parent.replay.yaml')
+Test.ATSReplayTest(replay_file='replays/bypass_parent_no_dns.replay.yaml')
+Test.ATSReplayTest(replay_file='replays/bypass_parent_plugin_parent.replay.yaml')
+Test.ATSReplayTest(replay_file='replays/bypass_parent_cache.replay.yaml')
+
+
+class BypassParentConnectTest:
+    '''CONNECT needs an outbound ip_allow rule for loopback, which ATSReplayTest cannot add.'''
+
+    replay_file = 'replays/bypass_parent_connect.replay.yaml'
+
+    def __init__(self):
+        self._server = Test.MakeVerifierServerProcess('server-connect', self.replay_file)
+        self._dns = Test.MakeDNServer('dns-connect', default='127.0.0.1')
+        self._server.Streams.stdout += Testers.ExcludesExpression(
+            'uuid: connect-', 'No CONNECT request reaches the server or the dead parent')
+        self._setup_ts()
+
+    def _setup_ts(self):
+        self._ts = Test.MakeATSProcess('ts-connect', enable_cache=False)
+        self._ts.Disk.records_config.update(
+            {
+                'proxy.config.diags.debug.enabled': 1,
+                'proxy.config.diags.debug.tags': 'http_trans|parent_select',
+                'proxy.config.dns.nameservers': f'127.0.0.1:{self._dns.Variables.Port}',
+                'proxy.config.dns.resolv_conf': 'NULL',
+                'proxy.config.http.connect_ports': f'{self._server.Variables.http_port}',

Review Comment:
   The CONNECT request in the replay targets port 80 (`connect-direct.test:80`), but `connect_ports` is set to the verifier server’s port. If `connect_ports` enforcement happens on the pre-remap CONNECT target port (80), this test can fail depending on implementation details. Consider allowing both ports (e.g., include `80` and the verifier port), or explicitly align `connect_ports` with the port that ATS validates for remapped CONNECT.



##########
tests/gold_tests/parent_proxy/bypass_parent.test.py:
##########
@@ -0,0 +1,80 @@
+'''
+Verify proxy.config.http.bypass_parent bypasses parent selection.
+'''
+#  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.
+
+Test.Summary = '''
+Verify proxy.config.http.bypass_parent bypasses parent.config, next-hop
+strategies, plugin-set parents, and CONNECT parenting, and yields to
+no_dns_just_forward_to_parent.
+'''
+
+Test.ATSReplayTest(replay_file='replays/bypass_parent.replay.yaml')
+Test.ATSReplayTest(replay_file='replays/bypass_parent_no_dns.replay.yaml')
+Test.ATSReplayTest(replay_file='replays/bypass_parent_plugin_parent.replay.yaml')
+Test.ATSReplayTest(replay_file='replays/bypass_parent_cache.replay.yaml')
+
+
+class BypassParentConnectTest:
+    '''CONNECT needs an outbound ip_allow rule for loopback, which ATSReplayTest cannot add.'''
+
+    replay_file = 'replays/bypass_parent_connect.replay.yaml'
+
+    def __init__(self):
+        self._server = Test.MakeVerifierServerProcess('server-connect', self.replay_file)
+        self._dns = Test.MakeDNServer('dns-connect', default='127.0.0.1')
+        self._server.Streams.stdout += Testers.ExcludesExpression(
+            'uuid: connect-', 'No CONNECT request reaches the server or the dead parent')
+        self._setup_ts()
+
+    def _setup_ts(self):
+        self._ts = Test.MakeATSProcess('ts-connect', enable_cache=False)
+        self._ts.Disk.records_config.update(
+            {
+                'proxy.config.diags.debug.enabled': 1,
+                'proxy.config.diags.debug.tags': 'http_trans|parent_select',
+                'proxy.config.dns.nameservers': f'127.0.0.1:{self._dns.Variables.Port}',
+                'proxy.config.dns.resolv_conf': 'NULL',
+                'proxy.config.http.connect_ports': f'{self._server.Variables.http_port}',
+                'proxy.config.http.parent_proxy.self_detect': 0,
+                'proxy.config.http.uncacheable_requests_bypass_parent': 0,
+                'proxy.config.http.parent_proxy.total_connect_attempts': 1,
+                'proxy.config.http.parent_proxy.per_parent_connect_attempts': 1,
+            })
+        self._ts.Disk.parent_config.AddLine('dest_domain=. parent="127.0.0.1:1|1" go_direct=false parent_is_proxy=true')
+        # Remap to a hostname: a 127.0.0.1 target would bypass the parent on its own as a localhost request.
+        server_port = self._server.Variables.http_port
+        self._ts.Disk.remap_config.AddLines(
+            [
+                f'map http://connect-direct.test:80/ http://origin.test:{server_port}/ '
+                '@plugin=conf_remap.so @pparam=proxy.config.http.bypass_parent=1',
+                f'map http://connect-parent.test:80/ http://origin.test:{server_port}/',
+            ])
+        self._ts.addPrivateConnectAllowYaml()
+
+    def run(self):
+        tr = Test.AddTestRun('bypass_parent bypasses the parent for CONNECT per remap rule')
+        tr.AddVerifierClientProcess('client-connect', self.replay_file, http_ports=[self._ts.Variables.port])
+        tr.Processes.Default.StartBefore(self._dns)
+        tr.Processes.Default.StartBefore(self._server)
+        tr.Processes.Default.StartBefore(self._ts)
+        tr.StillRunningAfter = self._dns
+        tr.StillRunningAfter = self._server
+        tr.StillRunningAfter = self._ts

Review Comment:
   These sequential assignments overwrite each other, so only the last one takes effect. If you intended to keep multiple processes alive, set `StillRunningAfter` once to the correct structure supported by the harness (e.g., a list/tuple), or remove the redundant lines if only `self._ts` is required.



##########
src/proxy/http/HttpTransact.cc:
##########
@@ -696,7 +696,21 @@ find_server_and_update_current_info(HttpTransact::State *s)
 {
   auto host{s->hdr_info.client_request.host_get()};
 
-  if (is_localhost(host)) {
+  // bypass_parent skips parent selection unless no_dns_just_forward_to_parent makes
+  // the parent responsible for reaching the origin.
+  bool bypass_parent = s->txn_conf->bypass_parent;
+  if (bypass_parent && s->txn_conf->no_dns_forward_to_parent) {
+    SiteThrottledWarning("proxy.config.http.bypass_parent is enabled, but "
+                         "proxy.config.http.no_dns_just_forward_to_parent prevents direct origin DNS; continuing with parent "
+                         "selection.");
+    bypass_parent = false;
+  }
+
+  if (bypass_parent) {
+    TxnDbg(dbg_ctl_http_trans, "bypassing parent selection due to proxy.config.http.bypass_parent (prior result %s)",
+           ParentResultStr[static_cast<int>(s->parent_result.result)]);
+    s->parent_result.result = ParentResultType::DIRECT;
+  } else if (is_localhost(host)) {

Review Comment:
   Forcing `s->parent_result.result` to `DIRECT` without clearing any other `parent_result` fields can leave stale parent/next-hop data from earlier selection (including plugin-set values) attached to the transaction state. If later code paths read other `parent_result` members (e.g., hostname/port/flags) without strictly gating on `result`, this can cause inconsistent behavior or misleading logging/metrics. Recommend explicitly resetting/clearing the remaining `parent_result` state when switching to `DIRECT` to keep the state self-consistent.



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@trafficserver.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org


Re: [PR] Add proxy.config.http.bypass_parent [trafficserver]

Posted by "traeak (via GitHub)" <gi...@apache.org>.
traeak commented on code in PR #13801:
URL: https://github.com/apache/trafficserver/pull/13801#discussion_r4230842288


##########
tests/gold_tests/parent_proxy/bypass_parent.test.py:
##########
@@ -0,0 +1,80 @@
+'''
+Verify proxy.config.http.bypass_parent bypasses parent selection.
+'''
+#  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.
+
+Test.Summary = '''
+Verify proxy.config.http.bypass_parent bypasses parent.config, next-hop
+strategies, plugin-set parents, and CONNECT parenting, and yields to
+no_dns_just_forward_to_parent.
+'''
+
+Test.ATSReplayTest(replay_file='replays/bypass_parent.replay.yaml')
+Test.ATSReplayTest(replay_file='replays/bypass_parent_no_dns.replay.yaml')
+Test.ATSReplayTest(replay_file='replays/bypass_parent_plugin_parent.replay.yaml')
+Test.ATSReplayTest(replay_file='replays/bypass_parent_cache.replay.yaml')
+
+
+class BypassParentConnectTest:
+    '''CONNECT needs an outbound ip_allow rule for loopback, which ATSReplayTest cannot add.'''
+
+    replay_file = 'replays/bypass_parent_connect.replay.yaml'
+
+    def __init__(self):
+        self._server = Test.MakeVerifierServerProcess('server-connect', self.replay_file)
+        self._dns = Test.MakeDNServer('dns-connect', default='127.0.0.1')
+        self._server.Streams.stdout += Testers.ExcludesExpression(
+            'uuid: connect-', 'No CONNECT request reaches the server or the dead parent')
+        self._setup_ts()
+
+    def _setup_ts(self):
+        self._ts = Test.MakeATSProcess('ts-connect', enable_cache=False)
+        self._ts.Disk.records_config.update(
+            {
+                'proxy.config.diags.debug.enabled': 1,
+                'proxy.config.diags.debug.tags': 'http_trans|parent_select',
+                'proxy.config.dns.nameservers': f'127.0.0.1:{self._dns.Variables.Port}',
+                'proxy.config.dns.resolv_conf': 'NULL',
+                'proxy.config.http.connect_ports': f'{self._server.Variables.http_port}',
+                'proxy.config.http.parent_proxy.self_detect': 0,
+                'proxy.config.http.uncacheable_requests_bypass_parent': 0,
+                'proxy.config.http.parent_proxy.total_connect_attempts': 1,
+                'proxy.config.http.parent_proxy.per_parent_connect_attempts': 1,
+            })
+        self._ts.Disk.parent_config.AddLine('dest_domain=. parent="127.0.0.1:1|1" go_direct=false parent_is_proxy=true')
+        # Remap to a hostname: a 127.0.0.1 target would bypass the parent on its own as a localhost request.
+        server_port = self._server.Variables.http_port
+        self._ts.Disk.remap_config.AddLines(
+            [
+                f'map http://connect-direct.test:80/ http://origin.test:{server_port}/ '
+                '@plugin=conf_remap.so @pparam=proxy.config.http.bypass_parent=1',
+                f'map http://connect-parent.test:80/ http://origin.test:{server_port}/',
+            ])
+        self._ts.addPrivateConnectAllowYaml()
+
+    def run(self):
+        tr = Test.AddTestRun('bypass_parent bypasses the parent for CONNECT per remap rule')
+        tr.AddVerifierClientProcess('client-connect', self.replay_file, http_ports=[self._ts.Variables.port])
+        tr.Processes.Default.StartBefore(self._dns)
+        tr.Processes.Default.StartBefore(self._server)
+        tr.Processes.Default.StartBefore(self._ts)
+        tr.StillRunningAfter = self._dns
+        tr.StillRunningAfter = self._server
+        tr.StillRunningAfter = self._ts

Review Comment:
   taken



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@trafficserver.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org


Re: [PR] Add proxy.config.http.bypass_parent [trafficserver]

Posted by "traeak (via GitHub)" <gi...@apache.org>.
traeak commented on PR #13801:
URL: https://github.com/apache/trafficserver/pull/13801#issuecomment-6081304837

   I decided to rename it to proxy.config.http.bypass_parent


-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@trafficserver.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org


Re: [PR] Add proxy.config.http.bypass_parent [trafficserver]

Posted by "traeak (via GitHub)" <gi...@apache.org>.
traeak commented on code in PR #13801:
URL: https://github.com/apache/trafficserver/pull/13801#discussion_r4230851152


##########
src/proxy/http/HttpTransact.cc:
##########
@@ -696,7 +696,21 @@ find_server_and_update_current_info(HttpTransact::State *s)
 {
   auto host{s->hdr_info.client_request.host_get()};
 
-  if (is_localhost(host)) {
+  // bypass_parent skips parent selection unless no_dns_just_forward_to_parent makes
+  // the parent responsible for reaching the origin.
+  bool bypass_parent = s->txn_conf->bypass_parent;
+  if (bypass_parent && s->txn_conf->no_dns_forward_to_parent) {
+    SiteThrottledWarning("proxy.config.http.bypass_parent is enabled, but "
+                         "proxy.config.http.no_dns_just_forward_to_parent prevents direct origin DNS; continuing with parent "
+                         "selection.");
+    bypass_parent = false;
+  }
+
+  if (bypass_parent) {
+    TxnDbg(dbg_ctl_http_trans, "bypassing parent selection due to proxy.config.http.bypass_parent (prior result %s)",
+           ParentResultStr[static_cast<int>(s->parent_result.result)]);
+    s->parent_result.result = ParentResultType::DIRECT;
+  } else if (is_localhost(host)) {

Review Comment:
   reset added



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@trafficserver.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org


Re: [PR] Add proxy.config.http.bypass_parent [trafficserver]

Posted by "traeak (via GitHub)" <gi...@apache.org>.
traeak commented on code in PR #13801:
URL: https://github.com/apache/trafficserver/pull/13801#discussion_r4230838152


##########
tests/gold_tests/parent_proxy/bypass_parent.test.py:
##########
@@ -0,0 +1,80 @@
+'''
+Verify proxy.config.http.bypass_parent bypasses parent selection.
+'''
+#  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.
+
+Test.Summary = '''
+Verify proxy.config.http.bypass_parent bypasses parent.config, next-hop
+strategies, plugin-set parents, and CONNECT parenting, and yields to
+no_dns_just_forward_to_parent.
+'''
+
+Test.ATSReplayTest(replay_file='replays/bypass_parent.replay.yaml')
+Test.ATSReplayTest(replay_file='replays/bypass_parent_no_dns.replay.yaml')
+Test.ATSReplayTest(replay_file='replays/bypass_parent_plugin_parent.replay.yaml')
+Test.ATSReplayTest(replay_file='replays/bypass_parent_cache.replay.yaml')
+
+
+class BypassParentConnectTest:
+    '''CONNECT needs an outbound ip_allow rule for loopback, which ATSReplayTest cannot add.'''
+
+    replay_file = 'replays/bypass_parent_connect.replay.yaml'
+
+    def __init__(self):
+        self._server = Test.MakeVerifierServerProcess('server-connect', self.replay_file)
+        self._dns = Test.MakeDNServer('dns-connect', default='127.0.0.1')
+        self._server.Streams.stdout += Testers.ExcludesExpression(
+            'uuid: connect-', 'No CONNECT request reaches the server or the dead parent')
+        self._setup_ts()
+
+    def _setup_ts(self):
+        self._ts = Test.MakeATSProcess('ts-connect', enable_cache=False)
+        self._ts.Disk.records_config.update(
+            {
+                'proxy.config.diags.debug.enabled': 1,
+                'proxy.config.diags.debug.tags': 'http_trans|parent_select',
+                'proxy.config.dns.nameservers': f'127.0.0.1:{self._dns.Variables.Port}',
+                'proxy.config.dns.resolv_conf': 'NULL',
+                'proxy.config.http.connect_ports': f'{self._server.Variables.http_port}',
+                'proxy.config.http.parent_proxy.self_detect': 0,
+                'proxy.config.http.uncacheable_requests_bypass_parent': 0,
+                'proxy.config.http.parent_proxy.total_connect_attempts': 1,
+                'proxy.config.http.parent_proxy.per_parent_connect_attempts': 1,
+            })
+        self._ts.Disk.parent_config.AddLine('dest_domain=. parent="127.0.0.1:1|1" go_direct=false parent_is_proxy=true')
+        # Remap to a hostname: a 127.0.0.1 target would bypass the parent on its own as a localhost request.
+        server_port = self._server.Variables.http_port
+        self._ts.Disk.remap_config.AddLines(
+            [
+                f'map http://connect-direct.test:80/ http://origin.test:{server_port}/ '
+                '@plugin=conf_remap.so @pparam=proxy.config.http.bypass_parent=1',
+                f'map http://connect-parent.test:80/ http://origin.test:{server_port}/',
+            ])
+        self._ts.addPrivateConnectAllowYaml()
+
+    def run(self):
+        tr = Test.AddTestRun('bypass_parent bypasses the parent for CONNECT per remap rule')
+        tr.AddVerifierClientProcess('client-connect', self.replay_file, http_ports=[self._ts.Variables.port])
+        tr.Processes.Default.StartBefore(self._dns)
+        tr.Processes.Default.StartBefore(self._server)
+        tr.Processes.Default.StartBefore(self._ts)
+        tr.StillRunningAfter = self._dns
+        tr.StillRunningAfter = self._server
+        tr.StillRunningAfter = self._ts

Review Comment:
   taken



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@trafficserver.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org


Re: [PR] Add proxy.config.http.bypass_parent [trafficserver]

Posted by "Copilot (via GitHub)" <gi...@apache.org>.
Copilot commented on code in PR #13801:
URL: https://github.com/apache/trafficserver/pull/13801#discussion_r4230618791


##########
tests/gold_tests/parent_proxy/bypass_parent.test.py:
##########
@@ -0,0 +1,80 @@
+'''
+Verify proxy.config.http.bypass_parent bypasses parent selection.
+'''
+#  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.
+
+Test.Summary = '''
+Verify proxy.config.http.bypass_parent bypasses parent.config, next-hop
+strategies, plugin-set parents, and CONNECT parenting, and yields to
+no_dns_just_forward_to_parent.
+'''
+
+Test.ATSReplayTest(replay_file='replays/bypass_parent.replay.yaml')
+Test.ATSReplayTest(replay_file='replays/bypass_parent_no_dns.replay.yaml')
+Test.ATSReplayTest(replay_file='replays/bypass_parent_plugin_parent.replay.yaml')
+Test.ATSReplayTest(replay_file='replays/bypass_parent_cache.replay.yaml')
+
+
+class BypassParentConnectTest:
+    '''CONNECT needs an outbound ip_allow rule for loopback, which ATSReplayTest cannot add.'''
+
+    replay_file = 'replays/bypass_parent_connect.replay.yaml'
+
+    def __init__(self):
+        self._server = Test.MakeVerifierServerProcess('server-connect', self.replay_file)
+        self._dns = Test.MakeDNServer('dns-connect', default='127.0.0.1')
+        self._server.Streams.stdout += Testers.ExcludesExpression(
+            'uuid: connect-', 'No CONNECT request reaches the server or the dead parent')
+        self._setup_ts()
+
+    def _setup_ts(self):
+        self._ts = Test.MakeATSProcess('ts-connect', enable_cache=False)
+        self._ts.Disk.records_config.update(
+            {
+                'proxy.config.diags.debug.enabled': 1,
+                'proxy.config.diags.debug.tags': 'http_trans|parent_select',
+                'proxy.config.dns.nameservers': f'127.0.0.1:{self._dns.Variables.Port}',
+                'proxy.config.dns.resolv_conf': 'NULL',
+                'proxy.config.http.connect_ports': f'{self._server.Variables.http_port}',
+                'proxy.config.http.parent_proxy.self_detect': 0,
+                'proxy.config.http.uncacheable_requests_bypass_parent': 0,
+                'proxy.config.http.parent_proxy.total_connect_attempts': 1,
+                'proxy.config.http.parent_proxy.per_parent_connect_attempts': 1,
+            })
+        self._ts.Disk.parent_config.AddLine('dest_domain=. parent="127.0.0.1:1|1" go_direct=false parent_is_proxy=true')
+        # Remap to a hostname: a 127.0.0.1 target would bypass the parent on its own as a localhost request.
+        server_port = self._server.Variables.http_port
+        self._ts.Disk.remap_config.AddLines(
+            [
+                f'map http://connect-direct.test:80/ http://origin.test:{server_port}/ '
+                '@plugin=conf_remap.so @pparam=proxy.config.http.bypass_parent=1',
+                f'map http://connect-parent.test:80/ http://origin.test:{server_port}/',
+            ])
+        self._ts.addPrivateConnectAllowYaml()
+
+    def run(self):
+        tr = Test.AddTestRun('bypass_parent bypasses the parent for CONNECT per remap rule')
+        tr.AddVerifierClientProcess('client-connect', self.replay_file, http_ports=[self._ts.Variables.port])
+        tr.Processes.Default.StartBefore(self._dns)
+        tr.Processes.Default.StartBefore(self._server)
+        tr.Processes.Default.StartBefore(self._ts)
+        tr.StillRunningAfter = self._dns
+        tr.StillRunningAfter = self._server
+        tr.StillRunningAfter = self._ts

Review Comment:
   These repeated assignments overwrite `StillRunningAfter`, so only the last process (`self._ts`) is retained. This can cause the DNS/server verifier processes to be treated as not-still-running (potentially leading to incorrect teardown/ordering or flakes). Set `StillRunningAfter` once with all required processes (e.g., assign a list/collection if supported by the harness), or use the harness’ additive API if one exists.



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@trafficserver.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org


Re: [PR] Add proxy.config.http.bypass_parent [trafficserver]

Posted by "traeak (via GitHub)" <gi...@apache.org>.
traeak commented on code in PR #13801:
URL: https://github.com/apache/trafficserver/pull/13801#discussion_r4232573404


##########
include/ts/apidefs.h.in:
##########
@@ -922,6 +922,7 @@ enum TSOverridableConfigKey {
   TS_CONFIG_HTTP_CACHE_MAX_STALE_AGE_PERCENT,
   TS_CONFIG_HTTP_PER_SERVER_CONNECTION_METRIC_ENABLED,
   TS_CONFIG_HTTP_PER_SERVER_CONNECTION_METRIC_AGGREGATE,
+  TS_CONFIG_HTTP_BYPASS_PARENT,
   TS_CONFIG_LAST_ENTRY,

Review Comment:
   autests use conf_remap plugin already which uses that mechanism.  unit tests already check every key.



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@trafficserver.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org


Re: [PR] Add proxy.config.http.bypass_parent [trafficserver]

Posted by "traeak (via GitHub)" <gi...@apache.org>.
traeak commented on code in PR #13801:
URL: https://github.com/apache/trafficserver/pull/13801#discussion_r4232258001


##########
doc/admin-guide/plugins/lua.en.rst:
##########
@@ -4821,6 +4821,7 @@ Http config constants
     TS_LUA_CONFIG_WEBSOCKET_NO_ACTIVITY_TIMEOUT
     TS_LUA_CONFIG_WEBSOCKET_ACTIVE_TIMEOUT
     TS_LUA_CONFIG_HTTP_UNCACHEABLE_REQUESTS_BYPASS_PARENT
+    TS_LUA_CONFIG_HTTP_BYPASS_PARENT

Review Comment:
   this is a different PR. All the surrounding defines are also added or exposed.



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: github-unsubscribe@trafficserver.apache.org

For queries about this service, please contact Infrastructure at:
users@infra.apache.org