Skip to content

Conversation

@smilkuri
Copy link
Contributor

@smilkuri smilkuri commented Nov 24, 2025

Issue #, if available:

#1779
codegen v3:aws/aws-sdk-js-v3#7549

Description of changes:

This fixes TypeScript client codegen conflict between known config keys and clientContextParams by adding the nested clientContextParams object to isolate conflicting parameters while maintaining backward compatibility and proper precedence.

--

@smilkuri smilkuri force-pushed the resolve-conflict-params branch from 4a0b1ea to c0cc0c7 Compare November 26, 2025 16:57
@smilkuri smilkuri force-pushed the resolve-conflict-params branch from f3ea1fe to 13fd0f0 Compare December 1, 2025 16:16
@smilkuri smilkuri marked this pull request as ready for review December 1, 2025 16:57
@smilkuri smilkuri requested a review from a team as a code owner December 1, 2025 16:57
@smilkuri smilkuri force-pushed the resolve-conflict-params branch 2 times, most recently from 9117008 to 1fc37f8 Compare December 1, 2025 17:01
@smilkuri smilkuri changed the title fix: nest conflicting endpoint parameters fix: handle clientContextParam collisions with builtin config keys Dec 1, 2025
@smilkuri smilkuri force-pushed the resolve-conflict-params branch from ef3cda8 to c5f0d86 Compare December 1, 2025 20:11
if (isClientContextParam) {
// For client context parameters, check clientContextParams first
const clientContextParams = config.clientContextParams as Record<string, unknown> | undefined;
const nestedValue: unknown = clientContextParams?.[configKey] ?? clientContextParams?.[canonicalEndpointParamKey];
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

is there any case where the nested object does not use the canonical parameter key?

If not, there's no reason to check the configKey entry for the nested object.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think so

type Provider,
ApiKeyIdentity,
ApiKeyIdentityProvider,
HttpApiKeyAuthLocation,
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

these new imports look like types. Change the codegen part to use addTypeImport() instead, or if imported via symbol, ensure the symbol has the typeOnly property.

*/
export interface EndpointParameters extends __EndpointParameters {
endpoint?: string | undefined;
endpoint: string;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

not saying it's wrong necessarily, but why did endpoint become required in the change?

@@ -1,5 +1,5 @@
// smithy-typescript generated code
import type { HttpAuthScheme } from "@smithy/types";
import { type HttpAuthScheme, ApiKeyIdentity, ApiKeyIdentityProvider } from "@smithy/types";
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

change these to type imports

type Provider,
ApiKeyIdentity,
ApiKeyIdentityProvider,
HttpApiKeyAuthLocation,
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

use type imports

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

HttpApiKeyAuthLocation can't be changed to type only. It's accessing a runtime value HttpApiKeyAuthLocation.HEADER

@smilkuri smilkuri force-pushed the resolve-conflict-params branch 3 times, most recently from 7016448 to 5401b57 Compare December 10, 2025 15:57
enableFeature: { type: "Boolean", required: true, default: true, documentation: "Feature toggle with default" }
debugMode: { type: "Boolean", required: true, default: false, documentation: "Debug mode with default" }
nonConflictingParam: { type: "String", required: true, default: "non-conflict-default", documentation: "Non-conflicting with default" }
logger: { type: "String", required: true, default: "default-logger", documentation: "Conflicting logger with default" }
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

all endpoint param types need to be lowercase string boolean. Add a stringArray one too, like "additionalFeatures".

@smilkuri smilkuri force-pushed the resolve-conflict-params branch from 5401b57 to c848d0a Compare December 11, 2025 18:44
@smilkuri smilkuri force-pushed the resolve-conflict-params branch from c848d0a to fee039f Compare December 11, 2025 18:48
// For client context parameters, check clientContextParams first
const clientContextParams = config.clientContextParams as Record<string, unknown> | undefined;
const nestedValue: unknown = clientContextParams?.[canonicalEndpointParamKey];
configValue = nestedValue ?? config[configKey] ?? config[canonicalEndpointParamKey];
Copy link
Contributor

@siddsriv siddsriv Dec 11, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

could canonicalEndpointParamKey and configKey differ? (ApiKey -- from the ruleset vs apiKey -- from the client config) would that create any problems for the precedence lookup?

Copy link
Contributor

@siddsriv siddsriv Dec 11, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

for example, would this case correctly prefer the nested value?

const client = new XYZService({
  apiKey: async () => ({ apiKey: "auth-secret" }),   
  clientContextParams: {
    apiKey: "endpoint-header-key"
  }
});

if the nested value looks for the canonical name, would it find ApiKey (name in commonParams) and then fall back to the root value when it doesn't find clientContextParams.[ApiKey]?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants