Skip to content

Commit 5933a33

Browse files
authored
[9.3] [Actions] Fix HTTP connector TLS options through proxies (#269898) (#274812)
# Backport This will backport the following commits from `main` to `9.3`: - [[Actions] Fix HTTP connector TLS options through proxies (#269898)](#269898) <!--- Backport version: 11.0.2 --> ### Questions ? Please refer to the [Backport tool documentation](https://github.com/sorenlouv/backport) <!--BACKPORT [{"author":{"name":"Shahar Glazner","email":"shaharglazner@gmail.com"},"sourceCommit":{"committedDate":"2026-05-20T08:50:22Z","message":"[Actions] Fix HTTP connector TLS options through proxies (#269898)\n\n## Summary\n- For HTTPS requests through an HTTP proxy, forward target TLS options\nto the CONNECT-upgraded request created by `HttpsProxyAgent`.\n- Ensures connector `verificationMode: none` and per-request SSL\noverrides like `fetcher.skip_ssl_verification` are honored when the\nproxy performs TLS inspection.\n- Adds a regression test covering target SSL overrides through the proxy\nagent callback.\n\n## Test plan\n- `node scripts/jest\nsrc/platform/packages/shared/kbn-actions-utils/utils/get_custom_agents.test.ts`\n- `node scripts/check_changes.ts`\n- Manually reproduced with local mitmproxy before the fix and verified\n`_execute` succeeds after the fix.\n\n## References\nCloses elastic/security-team#17454\nCloses https://github.com/elastic/kibana/issues/196602\n\nMade with [Cursor](https://cursor.com)\n\nCo-authored-by: Cursor <cursoragent@cursor.com>","sha":"4783bfafd2d0e25d59d5f2a835ef5f84defd1333","branchLabelMapping":{"^v9.5.0$":"main","^v(\\d+).(\\d+).\\d+$":"$1.$2"}},"sourcePullRequest":{"labels":["release_note:fix","backport:all-open","Team:One Workflow","v9.5.0","v9.4.2"],"title":"[Actions] Fix HTTP connector TLS options through proxies","number":269898,"url":"https://github.com/elastic/kibana/pull/269898","mergeCommit":{"message":"[Actions] Fix HTTP connector TLS options through proxies (#269898)\n\n## Summary\n- For HTTPS requests through an HTTP proxy, forward target TLS options\nto the CONNECT-upgraded request created by `HttpsProxyAgent`.\n- Ensures connector `verificationMode: none` and per-request SSL\noverrides like `fetcher.skip_ssl_verification` are honored when the\nproxy performs TLS inspection.\n- Adds a regression test covering target SSL overrides through the proxy\nagent callback.\n\n## Test plan\n- `node scripts/jest\nsrc/platform/packages/shared/kbn-actions-utils/utils/get_custom_agents.test.ts`\n- `node scripts/check_changes.ts`\n- Manually reproduced with local mitmproxy before the fix and verified\n`_execute` succeeds after the fix.\n\n## References\nCloses elastic/security-team#17454\nCloses https://github.com/elastic/kibana/issues/196602\n\nMade with [Cursor](https://cursor.com)\n\nCo-authored-by: Cursor <cursoragent@cursor.com>","sha":"4783bfafd2d0e25d59d5f2a835ef5f84defd1333"}},"sourceBranch":"main","suggestedTargetBranches":[],"targetPullRequestStates":[{"branch":"main","label":"v9.5.0","branchLabelMappingKey":"^v9.5.0$","isSourceBranch":true,"state":"MERGED","url":"https://github.com/elastic/kibana/pull/269898","number":269898,"mergeCommit":{"message":"[Actions] Fix HTTP connector TLS options through proxies (#269898)\n\n## Summary\n- For HTTPS requests through an HTTP proxy, forward target TLS options\nto the CONNECT-upgraded request created by `HttpsProxyAgent`.\n- Ensures connector `verificationMode: none` and per-request SSL\noverrides like `fetcher.skip_ssl_verification` are honored when the\nproxy performs TLS inspection.\n- Adds a regression test covering target SSL overrides through the proxy\nagent callback.\n\n## Test plan\n- `node scripts/jest\nsrc/platform/packages/shared/kbn-actions-utils/utils/get_custom_agents.test.ts`\n- `node scripts/check_changes.ts`\n- Manually reproduced with local mitmproxy before the fix and verified\n`_execute` succeeds after the fix.\n\n## References\nCloses elastic/security-team#17454\nCloses https://github.com/elastic/kibana/issues/196602\n\nMade with [Cursor](https://cursor.com)\n\nCo-authored-by: Cursor <cursoragent@cursor.com>","sha":"4783bfafd2d0e25d59d5f2a835ef5f84defd1333"}},{"branch":"9.4","label":"v9.4.2","branchLabelMappingKey":"^v(\\d+).(\\d+).\\d+$","isSourceBranch":false,"url":"https://github.com/elastic/kibana/pull/270104","number":270104,"state":"MERGED","mergeCommit":{"sha":"a52796fd91238e42d13f5044f0fd8958aabe08ee","message":"[9.4] [Actions] Fix HTTP connector TLS options through proxies (#269898) (#270104)\n\n# Backport\n\nThis will backport the following commits from `main` to `9.4`:\n- [[Actions] Fix HTTP connector TLS options through proxies\n(#269898)](https://github.com/elastic/kibana/pull/269898)\n\n\n\n### Questions ?\nPlease refer to the [Backport tool\ndocumentation](https://github.com/sorenlouv/backport)\n\n\n\nCo-authored-by: Shahar Glazner <shaharglazner@gmail.com>\nCo-authored-by: Cursor <cursoragent@cursor.com>"}},{"url":"https://github.com/elastic/kibana/pull/272321","number":272321,"branch":"8.19","state":"OPEN"}]}] BACKPORT--> --- **Note:** This PR was created with conflicts auto-resolved in favor of the source commit (`--strategy-option=theirs`). Please review the changes carefully.
1 parent 6c75d77 commit 5933a33

2 files changed

Lines changed: 76 additions & 10 deletions

File tree

src/platform/packages/shared/kbn-actions-utils/utils/get_custom_agents.test.ts

Lines changed: 44 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,50 @@ describe('getCustomAgents', () => {
5252
expect(httpsAgent instanceof HttpsProxyAgent).toBeTruthy();
5353
});
5454

55+
test('passes target SSL overrides to the CONNECT-upgraded TLS request', async () => {
56+
const callbackSpy = jest
57+
.spyOn(HttpsProxyAgent.prototype, 'callback')
58+
.mockResolvedValue({} as Awaited<ReturnType<HttpsProxyAgent['callback']>>);
59+
const proxySettings = {
60+
proxyUrl: 'http://someproxyhost',
61+
proxySSLSettings: {
62+
verificationMode: 'full',
63+
},
64+
proxyBypassHosts: undefined,
65+
proxyOnlyHosts: undefined,
66+
} as ProxySettings;
67+
68+
const { httpsAgent } = getCustomAgents({
69+
logger,
70+
proxySettings,
71+
sslOverrides: {
72+
verificationMode: 'none',
73+
},
74+
sslSettings: defaultSSLSettings,
75+
url: targetUrl,
76+
});
77+
78+
try {
79+
await (httpsAgent as unknown as HttpsProxyAgent).callback(
80+
{} as Parameters<HttpsProxyAgent['callback']>[0],
81+
{
82+
host: targetHost,
83+
port: 443,
84+
secureEndpoint: true,
85+
} as Parameters<HttpsProxyAgent['callback']>[1]
86+
);
87+
88+
expect(callbackSpy).toHaveBeenCalledWith(
89+
expect.anything(),
90+
expect.objectContaining({
91+
rejectUnauthorized: false,
92+
})
93+
);
94+
} finally {
95+
callbackSpy.mockRestore();
96+
}
97+
});
98+
5599
test('return default agents for invalid proxy URL', () => {
56100
const proxySettings = {
57101
proxyUrl: ':nope: not a valid URL',

src/platform/packages/shared/kbn-actions-utils/utils/get_custom_agents.ts

Lines changed: 32 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,24 @@ interface GetCustomAgentsOpts {
3333
url: string;
3434
}
3535

36+
class TargetSslHttpsProxyAgent extends HttpsProxyAgent {
37+
constructor(
38+
proxyOptions: ConstructorParameters<typeof HttpsProxyAgent>[0],
39+
private readonly targetSSLOptions: AgentOptions
40+
) {
41+
super(proxyOptions);
42+
}
43+
44+
callback(
45+
req: Parameters<HttpsProxyAgent['callback']>[0],
46+
opts: Parameters<HttpsProxyAgent['callback']>[1]
47+
) {
48+
// HttpsProxyAgent constructor options configure the proxy connection. Target TLS
49+
// options must be merged into the CONNECT-upgraded request options instead.
50+
return super.callback(req, { ...opts, ...this.targetSSLOptions });
51+
}
52+
}
53+
3654
export function getCustomAgents(opts: GetCustomAgentsOpts): GetCustomAgentsResponse {
3755
const {
3856
customHostSettings,
@@ -135,20 +153,24 @@ export function getCustomAgents(opts: GetCustomAgentsOpts): GetCustomAgentsRespo
135153
// We will though, copy over the calculated ssl options from above, into
136154
// the https agent.
137155
const httpAgent = new HttpProxyAgent(proxySettings.proxyUrl) as unknown as HttpAgent;
138-
const httpsAgent = new HttpsProxyAgent({
139-
host: proxyUrl.hostname,
140-
port: Number(proxyUrl.port),
141-
protocol: proxyUrl.protocol,
142-
headers: proxySettings.proxyHeaders,
143-
// do not fail on invalid certs if value is false
144-
...proxyNodeSSLOptions,
145-
}) as unknown as HttpsAgent;
156+
const targetSSLOptions = agentOptions ?? agentSSLOptions;
157+
const httpsAgent = new TargetSslHttpsProxyAgent(
158+
{
159+
host: proxyUrl.hostname,
160+
port: Number(proxyUrl.port),
161+
protocol: proxyUrl.protocol,
162+
headers: proxySettings.proxyHeaders,
163+
// do not fail on invalid certs if value is false
164+
...proxyNodeSSLOptions,
165+
},
166+
targetSSLOptions
167+
) as unknown as HttpsAgent;
146168
// vsCode wasn't convinced HttpsProxyAgent is an https.Agent, so we convinced it
147169

148-
if (agentOptions) {
170+
if (targetSSLOptions) {
149171
httpsAgent.options = {
150172
...httpsAgent.options,
151-
...agentOptions,
173+
...targetSSLOptions,
152174
};
153175
}
154176

0 commit comments

Comments
 (0)