Skip to content

create smithy plugin to generate BDD ruleset - #3880

Open
sbiscigl wants to merge 1 commit into
mainfrom
generate-bdd-rulesset
Open

create smithy plugin to generate BDD ruleset#3880
sbiscigl wants to merge 1 commit into
mainfrom
generate-bdd-rulesset

Conversation

@sbiscigl

Copy link
Copy Markdown
Collaborator

Issue #, if available:

#2880

Description of changes:

Adds a flag --use-smithy-bdd-endpoints that will enable a smithy plugin to generate a BDD rules set representation and swap clients to use a BDD endpoint provider by default. from preliminary testing we see a large reduction in client contruction time and endpoints resolution time in the S3 Client

Benchmark JSON BDD Δ Speedup
s3 client construction 750,135 ns 30,639 ns −95.9% 24.5×
steady state resolve on virtual addressing 6,006 ns 3,312 ns −44.9% 1.81×

This PR will NOT trigger generation, a follow up PR will swap the default value, and move clients to the new endpoint provider.

Check all that applies:

  • Did a review by yourself.
  • Added proper tests to cover this PR. (If tests are not applicable, explain.)
  • Checked if this PR is a breaking (APIs have been changed) change.
  • Checked if this PR will not introduce cross-platform inconsistent behavior.
  • Checked if this PR would require a ReadMe/Wiki update.

Check which platforms you have built SDK on to verify the correctness of this PR.

  • Linux
  • Windows
  • Android
  • MacOS
  • IOS
  • Other Platforms

By submitting this pull request, I confirm that you can use, modify, copy, and redistribute this contribution, under the terms of your choice.

@sbiscigl
sbiscigl marked this pull request as ready for review July 27, 2026 17:56
@sbiscigl
sbiscigl force-pushed the generate-bdd-rulesset branch 5 times, most recently from 096fed7 to 5b2d183 Compare July 27, 2026 20:12
@sbiscigl
sbiscigl force-pushed the generate-bdd-rulesset branch from 5b2d183 to 7f5708e Compare July 27, 2026 20:47
return {
smithy_to_c2j.get(sdk_id, sdk_id)
for sdk_id in (f[:-len(".json")] for f in os.listdir(descriptions_dir) if f.endswith(".json"))
if ENDPOINT_BDD_TRAIT in Path(descriptions_dir, sdk_id + ".json").read_text()

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

nit: Could this false-positive if smithy.rules#endpointBdd appears in a documentation field or other string value in the JSON? It's a substring search over the entire file contents.

smithy_to_c2j.get(sdk_id, sdk_id)
for sdk_id in (f[:-len(".json")] for f in os.listdir(descriptions_dir) if f.endswith(".json"))
if ENDPOINT_BDD_TRAIT in Path(descriptions_dir, sdk_id + ".json").read_text()
}

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

A substring search in the entire model seems shady to me, can we use actual json/trait parsing since we know exactly where this trait will live on the model?

ex.

def bdd_endpoint_services():
      """C2J service names whose Smithy model carries the endpointBdd trait on its service shape,
      i.e. the services the Smithy generator will emit a BDD blob for. C2J must skip its JSON
      endpoint-rules blob for exactly this set; services outside it (legacy/mock, or models lacking
      the trait) keep the JSON path. This MUST stay in sync with EndpointRulesCodegenPlugin's
      service.hasTrait(ENDPOINT_BDD_TRAIT) check — divergence causes a missing GetRulesBlob() symbol."""
      with open(os.path.abspath(SMITHY_TO_C2J_MAP_FILE), 'r') as file:
          smithy_to_c2j = json.load(file)
      descriptions_dir = os.path.abspath(SMITHY_API_DESCRIPTIONS_DIR)
      services = set()
      for f in os.listdir(descriptions_dir):
          if not f.endswith(".json"):
              continue
          sdk_id = f[:-len(".json")]
          model = json.loads(Path(descriptions_dir, f).read_text())
          has_bdd = any(
              shape.get("type") == "service" and ENDPOINT_BDD_TRAIT in shape.get("traits", {})
              for shape in model.get("shapes", {}).values()
          )
          if has_bdd:
              services.add(smithy_to_c2j.get(sdk_id, sdk_id))
      return services

private static String sanitize(String s) {
return s.replace(" ", "").replace("-", "").replace("_", "")
.replace("Amazon", "").replace("AWS", "").replace("/", "");
}

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

We're duplicating functionality here. ServiceNameUtilJava.sanitizeServiceAbbreviation does this already

return String.format("'\\x%02x'", b & 0xFF);
}

private static String toLocalMacro(String exportMacro) {

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

Eventually we'll need this functionality for client generation. Should this be in ServiceNameUtil?

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.

4 participants